MeshCentral/agents/meshcmd.js

3200 lines
636 KiB
JavaScript
Raw Normal View History

/*
2021-01-09 17:31:09 -05:00
Copyright 2018-2021 Intel Corporation
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
/**
* @description MeshCmd, command line tool for Intel AMT and MeshCentral.
* @author Ylian Saint-Hilaire
* @version v0.2.0
*/
// Debug Stuff
//console.displayFinalizerMessages = 1; // Display objects that have event listeners that are disposed.
//console.displayStreamPipeMessages = 1; // Display stream pipe and un-pipes
//var __gc = setInterval(function () { console.log('GC'); _debugGC() }, 2000); //
var fs = require('fs');
var os = require('os');
var net = require('net');
var http = require('http');
var dgram = require('dgram');
var httpHeaders = require('http-headers');
var tcpserver = null;
var broadcastSockets = {};
var multicastSockets = {};
var discoveryInterval = null;
var membershipIPv4 = '239.255.255.235';
var membershipIPv6 = 'FF02:0:0:0:0:0:0:FE';
var settings = null;
var meshCmdVersion = '***Mesh*Cmd*Version***'; // Dynamically replaced with MeshCentral version
var amtLms = null, amtMei = null, amtMeiState = null;
var wsstack = null, amtstack = null;
var oswsstack = null, osamtstack = null;
var amtMeiTmpState = null;
var SMBiosTables = null;
var globalDebugFlags = 0; // 1 = IDER Debug
var pendingAmtConfigActions = 0;
var RCSMessageProtocolVersion = 1; // RCS Message Protocol Version. Needs to be less than or equal to RCS server Message Protocol Version
2022-03-23 14:05:52 -04:00
// MeshCommander LMS (GZIP'ed, Base64) v0.9.5
var _IntelAmtWebApp_etag = "T7RH5C+aqW17rf2VRePh";
var _IntelAmtWebApp = "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
2022-03-23 14:05:52 -04:00
// MeshCommander Local (GZIP'ed, Base64) v0.9.5
var FullSite_IntelAmtLocalWebApp_etag = "6YwflPJ3fhVn3bz5paH8";
var FullSite_IntelAmtLocalWebApp = "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
// Check the server certificate fingerprint
function onVerifyServer(clientName, certs) {
if (certs == null) { certs = clientName; } // Temporary thing until we fix duktape
// If we have the serverid, used delayed server authentication
2021-05-25 19:35:55 -04:00
if (settings.serverid != null) { settings.meshServerTlsHash = certs[0].fingerprint.replace(/:/g, ''); return; }
// Otherwise, use server HTTPS certificate hash
try { for (var i in certs) { if (certs[i].fingerprint.replace(/:/g, '') == settings.serverhttpshash) { return; } } } catch (e) { }
if (settings.serverhttpshash != null) {
console.log('Error: Failed to verify server certificate.');
console.log('Server TLS hash: ' + certs[i].fingerprint.replace(/:/g, ''));
exit(255);
throw 'Invalid server certificate';
}
}
// Various utility functions
function debug(level, message) { if ((settings.debuglevel != null) && (settings.debuglevel >= level)) { console.log(message); } }
function exit(status) { if (status == null) { status = 0; } try { process.exit(status); } catch (e) { } }
function getInstance(x, y) { for (var i in x) { if (x[i]["InstanceID"] == y) return x[i]; } return null; }
function md5hex(str) { return require('MD5Stream').create().syncHash(str).toString('hex'); }
function guidToStr(g) { return g.substring(6, 8) + g.substring(4, 6) + g.substring(2, 4) + g.substring(0, 2) + "-" + g.substring(10, 12) + g.substring(8, 10) + "-" + g.substring(14, 16) + g.substring(12, 14) + "-" + g.substring(16, 20) + "-" + g.substring(20); }
function parceArguments(argv) { var r = {}; for (var i in argv) { i = parseInt(i); if (argv[i].startsWith('--') == true) { var key = argv[i].substring(2).toLowerCase(), val = true; if (((i + 1) < argv.length) && (argv[i + 1].startsWith('--') == false)) { val = argv[i + 1]; } r[key] = val; } } return r; }
// Convert an object to string with all functions
function objToString(x, p, ret) {
if (ret == undefined) ret = '';
if (p == undefined) p = 0;
if (x == null) { return '[null]'; }
if (p > 8) { return '[...]'; }
if (x == undefined) { return '[undefined]'; }
if (typeof x == 'string') { if (p == 0) return x; return '"' + (x.split('\0')[0]) + '"'; }
if (typeof x == 'buffer') { return '[buffer]'; }
if (typeof x != 'object') { return x; }
var r = '{' + (ret ? '\r\n' : ' ');
for (var i in x) {
if (i != '_ObjectID') { r += (addPad(p + 2, ret) + i + ': ' + objToString(x[i], p + 2, ret) + (ret ? '\r\n' : ' ')); }
}
return r + addPad(p, ret) + '}';
}
// Return p number of spaces
function addPad(p, ret) { var r = ''; for (var i = 0; i < p; i++) { r += ' '; } return r; }
// Parse the incoming arguments
function run(argv) {
if (meshCmdVersion[0] == '*') { meshCmdVersion = ''; } else { meshCmdVersion = ' v' + meshCmdVersion; }
var args = parceArguments(argv);
//console.log(JSON.stringify(argv));
//console.log('addedModules = ' + JSON.stringify(addedModules));
var actionpath = 'meshaction.txt';
if (args.actionfile != null) { actionpath = args.actionfile; }
var actions = ['HELP', 'ROUTE', 'MICROLMS', 'AMTCONFIG', 'AMTSCAN', 'AMTPOWER', 'AMTFEATURES', 'AMTNETWORK', 'AMTINFO', 'AMTINFOJSON', 'AMTVERSIONS', 'AMTHASHES', 'AMTSAVESTATE', 'AMTUUID', 'AMTCCM', 'AMTDEACTIVATE', 'AMTACMDEACTIVATE', 'SMBIOS', 'RAWSMBIOS', 'MESHCOMMANDER', 'AMTAUDITLOG', 'AMTEVENTLOG', 'AMTPRESENCE', 'AMTWIFI', 'AMTWAKE', 'AMTSTARTCONFIG', 'AMTSTOPCONFIG', 'AMTDDNS'];
// Load the action file
var actionfile = null;
try { actionfile = fs.readFileSync(actionpath); } catch (e) { }
if ((actionpath != 'meshaction.txt') && (actionfile == null)) { console.log('Unable to load \"' + actionpath + '\". Create this file or specify the location using --actionfile [filename].'); exit(1); return; }
if (actionfile != null) { try { settings = JSON.parse(actionfile); } catch (e) { console.log(actionpath, e); exit(1); return; } } else { if (argv.length >= 2) { settings = { action: argv[1] } } }
if (settings == null) { settings = {}; }
var settings2 = {}; for (var i in settings) { settings2[i.toLowerCase()] = settings[i]; } settings = settings2;
// Set the arguments
if ((typeof args.action) == 'string') { settings.action = args.action; }
if ((typeof args.authcookie) == 'string') { settings.authcookie = args.authcookie; }
if ((typeof args.localport) == 'string') { settings.localport = parseInt(args.localport); }
if ((typeof args.remotenodeid) == 'string') { settings.remotenodeid = args.remotenodeid; }
if ((typeof args.name) == 'string') { settings.name = args.name; }
if ((typeof args.id) == 'string') { settings.id = args.id; }
if ((typeof args.username) == 'string') { settings.username = args.username; }
if ((typeof args.password) == 'string') { settings.password = args.password; }
if ((typeof args.url) == 'string') { settings.url = args.url; }
if ((typeof args.type) == 'string') { settings.type = args.type; }
if ((typeof args.user) == 'string') { settings.username = args.user; }
if ((typeof args.pass) == 'string') { settings.password = args.pass; }
if ((typeof args.host) == 'string') { settings.hostname = args.host; }
if ((typeof args.hostname) == 'string') { settings.hostname = args.hostname; }
if ((typeof args.serverid) == 'string') { settings.serverid = args.serverid; }
if ((typeof args.serverhttpshash) == 'string') { settings.serverhttpshash = args.serverhttpshash; }
if ((typeof args.serverurl) == 'string') { settings.serverurl = args.serverurl; }
if ((typeof args.remoteport) == 'string') { settings.remoteport = parseInt(args.remoteport); }
if ((typeof args.remotetarget) == 'string') { settings.remotetarget = args.remotetarget; }
if ((typeof args.out) == 'string') { settings.output = args.out; }
if ((typeof args.output) == 'string') { settings.output = args.output; }
if ((typeof args.debug) == 'string') { settings.debuglevel = parseInt(args.debug); }
if ((typeof args.debugflags) == 'string') { globalDebugFlags = parseInt(args.debugflags); }
if ((typeof args.script) == 'string') { settings.script = args.script; }
if ((typeof args.agent) == 'string') { settings.agent = args.agent; }
if ((typeof args.proxy) == 'string') { settings.proxy = args.proxy; }
if ((typeof args.floppy) == 'string') { settings.floppy = args.floppy; }
if ((typeof args.cdrom) == 'string') { settings.cdrom = args.cdrom; }
if ((typeof args.tag) == 'string') { settings.tag = args.tag; }
if ((typeof args.scan) == 'string') { settings.scan = args.scan; }
if ((typeof args.token) == 'string') { settings.token = args.token; }
if ((typeof args.timeout) == 'string') { settings.timeout = parseInt(args.timeout); }
if ((typeof args.iderstart) == 'string') { settings.iderstart = args.iderstart; }
if ((typeof args.uuidoutput) == 'string' || args.uuidoutput) { settings.uuidoutput = args.uuidoutput; }
if ((typeof args.desc) == 'string') { settings.desc = args.desc; }
if ((typeof args.dnssuffix) == 'string') { settings.dnssuffix = args.dnssuffix; }
if (args.emailtoken) { settings.emailtoken = true; }
2021-03-24 16:36:23 -04:00
if (args.smstoken) { settings.smstoken = true; }
if (args.debug === true) { settings.debuglevel = 1; }
if (args.debug) { try { waitForDebugger(); } catch (e) { } }
if (args.noconsole) { settings.noconsole = true; }
if (args.nocommander) { settings.noconsole = true; }
if (args.lmsdebug) { settings.lmsdebug = true; }
if (args.json) { settings.json = true; }
if (args.tls) { settings.tls = true; }
if ((argv.length > 1) && (actions.indexOf(argv[1].toUpperCase()) >= 0)) { settings.action = argv[1]; }
if (globalDebugFlags != 0) { console.setInfoLevel(1); }
// Validate meshaction.txt
if (settings.action == null) {
console.log('MeshCentral Command (MeshCmd) ' + meshCmdVersion);
console.log('No action specified, use MeshCmd like this:\r\n');
console.log(' meshcmd [action] [arguments...]\r\n');
console.log('Valid MeshCentral actions:');
console.log(' Route - Map a local TCP port to a remote computer.');
console.log(' AmtConfig - Setup Intel AMT on this computer.');
console.log('\r\nValid local actions:');
console.log(' SMBios - Display System Management BIOS tables for this computer.');
console.log(' RawSMBios - Display RAW System Management BIOS tables for this computer.');
console.log(' MicroLMS - Run MicroLMS, allowing local access to Intel AMT.');
console.log(' AmtInfo - Show Intel AMT version and activation state.');
console.log(' AmtVersions - Show all Intel ME version information.');
console.log(' AmtHashes - Show all Intel AMT trusted activation hashes.');
console.log(' AmtCCM - Activate Intel AMT into Client Control Mode.');
console.log(' AmtDeactivate - Deactivate Intel AMT if activated in Client Control mode.');
console.log(' AmtAcmDeactivate - Deactivate Intel AMT if activated in Admin Control mode.');
console.log('\r\nValid local or remote actions:');
console.log(' MeshCommander - Launch a local MeshCommander web server.');
console.log(' AmtUUID - Show Intel AMT unique identifier.');
console.log(' AmtEventLog - Show the Intel AMT event log.');
console.log(' AmtAuditLog - Show the Intel AMT audit log.');
console.log(' AmtSaveState - Save all Intel AMT WSMAN object to file.');
console.log(' AmtPresence - Heartbeat a local Intel AMT watchdog agent.');
console.log(' AmtPower - Perform remote Intel AMT power operation.');
console.log(' AmtIDER - Mount local disk image to remote computer.');
console.log(' AmtFeatures - Intel AMT features & user consent.');
console.log(' AmtNetwork - Intel AMT network interface settings.');
console.log(' AmtScan - Search local network for Intel AMT devices.');
console.log(' AmtWifi - Intel AMT Wifi interface settings.');
console.log(' AmtWake - Intel AMT Wake Alarms.');
console.log(' AmtRPE - Intel AMT Remote Platform Erase.');
console.log(' AmtDDNS - Intel AMT DDNS settings.');
console.log('\r\nHelp on a specific action using:\r\n');
console.log(' meshcmd help [action]');
2021-07-16 21:43:30 -04:00
exit(0); return;
}
if (settings.action == 'help') {
if (argv.length <= 2) {
actions.shift();
console.log('Help usage:\r\n\r\n MeshCmd help [action]\r\n\r\nValid actions are: ' + actions.join(', ') + '.');
2021-07-16 21:43:30 -04:00
exit(0); return;
}
var action = argv[2].toLowerCase();
if (action == 'route') {
console.log("The route action is used along with a MeshCentral account to map a local TCP port to a remote port on any computer on your MeshCentral account. This action requires many arguments, to avoid specifying them all it's best to download the meshaction.txt file from the web site and place it in the current folder. Example usage:\r\n\r\n (Place meshaction.txt file in current folder)\r\n meshcmd route --pass myAccountPassword");
} else if (action == 'smbios') {
console.log("SMBios action will display this computer's system management BIOS information. Example usage:\r\n\r\n meshcmd smbios --out smbios.txt\r\n");
console.log('\r\Optional arguments:\r\n');
console.log(' --output [filename] Optional filename to write the results to.');
} else if (action == 'rawsmbios') {
console.log("RawSMBios action will display this computer's system management BIOS information in raw hexdecimal form. Example usage:\r\n\r\n meshcmd rawsmbios --out smbios.txt\r\n");
console.log('\r\Optional arguments:\r\n');
console.log(' --output [filename] Optional filename to write the results to.');
} else if (action == 'amtinfo') {
console.log('AmtInfo action will get the version and activation state of Intel AMT on this computer. The command must be run on a computer with Intel AMT, must run as administrator and the Intel management driver must be installed. Example usage:\r\n\r\n meshcmd amtinfo');
console.log('\r\nPossible arguments:\r\n');
console.log(' --json Display all Intel AMT state in JSON format.');
} else if (action == 'amtinfojson') {
console.log('AmtInfoJson action get Intel AMT information about the computer and display it or send it to a server using HTTP. Example usage:\r\n\r\n meshcmd amtinfojson --post https://example.com/capture');
console.log('\r\nPossible arguments:\r\n');
console.log(' --post [url] Perform an HTTP POST of the data to the given URL.');
} else if ((action == 'amtversion') || (action == 'amtversions')) {
console.log('AmtVersions will display all version information about Intel AMT on this computer. The command must be run on a computer with Intel AMT, must run as administrator and the Intel management driver must be installed. Example usage:\r\n\r\n meshcmd amtversions');
console.log('\r\nPossible arguments:\r\n');
console.log(' --json Display all Intel AMT state in JSON format.');
} else if (action == 'amthashes') {
console.log('Amthashes will display all trusted activations hashes for Intel AMT on this computer. The command must be run on a computer with Intel AMT, must run as administrator and the Intel management driver must be installed. These certificates hashes are used by Intel AMT when performing activation into ACM mode. Example usage:\r\n\r\n meshcmd amthashes');
2021-07-16 21:43:30 -04:00
console.log('\r\nPossible arguments:\r\n');
console.log(' --json Display all Intel AMT hashes in JSON format.');
} else if ((action == 'microlms') || (action == 'lms') || (action == 'amtlms')) {
console.log('Starts MicroLMS on this computer, allowing local access to Intel AMT on TCP ports 16992 and 16993 when applicable. The command must be run on a computer with Intel AMT, must run as administrator and the Intel management driver must be installed. These certificates hashes are used by Intel AMT when performing activation into ACM mode. Example usage:\r\n\r\n meshcmd microlms');
console.log('\r\nPossible arguments:\r\n');
console.log(' --noconsole MeshCommander for LMS will no be available on port 16994.');
console.log('\r\nRun as a background service:\r\n');
console.log(' microlms install/uninstall/start/stop.');
} else if (action == 'amtccm') {
console.log('AmtCCM will attempt to activate Intel AMT on this computer into client control mode (CCM). The command must be run on a computer with Intel AMT, must run as administrator and the Intel management driver must be installed. Intel AMT must be in "pre-provisioning" state for this command to work and a administrator password must be provided.');
console.log('\r\nPossible arguments:\r\n');
console.log(' --password [password] Admin password used to activate Intel AMT.');
} else if (action == 'amtconfig') {
console.log('AmtConfig will attempt to activate and configure Intel AMT on this computer. The command must be run on a computer with Intel AMT, must run as administrator and the Intel management driver must be installed. Example usage:\r\n\r\n meshcmd amtconfig --url [url]');
console.log('\r\nPossible arguments:\r\n');
console.log(' --url [wss://server] The address of the MeshCentral server.');
console.log(' --id [groupid] The device group identifier.');
console.log(' --serverhttpshash [hash] Optional TLS server certificate hash.');
console.log(' --user [username] The Intel AMT admin username, admin is default.');
console.log(' --pass [password] The Intel AMT admin password.');
console.log(' --desc [description] Description of the device, used when first added to server.');
console.log(' --dnssuffix [dns] Override the trusted DNS suffix sent to the server.');
} else if (action == 'amtdeactivate') {
console.log('AmtDeactivate will attempt to deactivate Intel AMT on this computer when in client control mode (CCM). The command must be run on a computer with Intel AMT, must run as administrator and the Intel management driver must be installed. Intel AMT must be activated in client control mode for this command to work. Example usage:\r\n\r\n meshcmd amtdeactivate');
} else if (action == 'amtacmdeactivate') {
console.log('AmtACMDeactivate will attempt to deactivate Intel AMT on this computer when in admin control mode (ACM). The command must be run on a computer with Intel AMT, must run as administrator and the Intel management driver must be installed. Intel AMT must be activated in admin control mode for this command to work. Example usage:\r\n\r\n meshcmd amtacmdeactivate');
console.log('\r\nPossible arguments:\r\n');
console.log(' --user [username] The Intel AMT login username, admin is default.');
console.log(' --pass [password] The Intel AMT login password.');
console.log(' --type [partial/full] Specifies to perform partial or full unprovision.');
} else if (action == 'amtuuid') {
console.log('AmtUUID action will get the unique identifier of the local or remote Intel AMT computer. By default, the local UUID is obtained unless a host is specified. Intel AMT must be activated for this command to work. Example usage:\r\n\r\n meshcmd amtuuid --host 1.2.3.4 --user admin --pass mypassword --tls');
console.log('\r\nPossible arguments:\r\n');
console.log(' --host [hostname] The IP address or DNS name of Intel AMT, 127.0.0.1 is default.');
console.log(' --user [username] The Intel AMT login username, admin is default.');
console.log(' --pass [password] The Intel AMT login password.');
console.log(' --tls Specifies that TLS must be used.');
} else if (action == 'amtsavestate') {
console.log('AmtSaveState action will fetch all the entire state of Intel AMT and save it as a JSON file. This action will take multiple minutes to perform. The command will fetch the local computer state unless host is specified. Intel AMT must be ativated for this command to work. Example usage:\r\n\r\n meshcmd amtsavestate --host 1.2.3.4 --user admin --pass mypassword --tls --output state.json');
console.log('\r\nPossible arguments:\r\n');
console.log(' --output [filename] The output file for the Intel AMT state in JSON format.');
console.log(' --host [hostname] The IP address or DNS name of Intel AMT, 127.0.0.1 is default.');
console.log(' --user [username] The Intel AMT login username, admin is default.');
console.log(' --pass [password] The Intel AMT login password.');
console.log(' --tls Specifies that TLS must be used.');
} else if (action == 'amtpresence') {
console.log('AmtPresence will heartbeat a local Intel AMT watchdog agent. Example usage:\r\n\r\n meshcmd amtpresence --agent B4B6A24C-255E-A75C-F5E8-B00B4D946AA7');
console.log('\r\nPossible arguments:\r\n');
console.log(' --user [username] The Intel AMT login username, admin is default.');
console.log(' --pass [password] The Intel AMT login password.');
console.log(' --agent [uuid] The unique identifier of the watchdog agent.');
} else if (action == 'amtpower') {
console.log('AmtPower will get current pwoer state or send a reboot command to a remote Intel AMT device. Example usage:\r\n\r\n meshcmd amtpower --reset --host 1.2.3.4 --user admin --pass mypassword --tls');
console.log('\r\nRequired arguments:\r\n');
console.log(' --host [hostname] The IP address or DNS name of Intel AMT.');
console.log(' --pass [password] The Intel AMT login password.');
console.log('\r\nOptional arguments:\r\n');
console.log(' --reset, --poweron, --poweroff, --powercycle, --sleep, --hibernate');
console.log(' --user [username] The Intel AMT login username, admin is default.');
console.log(' --tls Specifies that TLS must be used.');
console.log(' --bootdevice [pxe|hdd|cd|ider-floppy|ider-cdrom] Specifies the boot device to use after reset, poweron or powercycle.');
console.log(' --bootindex [number] Specifies the index of boot device to use.');
} else if (action == 'amtnetwork') {
console.log('AmtNetwork is used to get/set Intel AMT network interface configuration. Example usage:\r\n\r\n meshcmd amtnetwork --host 1.2.3.4 --user admin --pass mypassword --dhcp');
console.log('\r\nRequired arguments:\r\n');
console.log(' --host [hostname] The IP address or DNS name of Intel AMT, 127.0.0.1 is default.');
console.log(' --pass [password] The Intel AMT login password.');
console.log('\r\nOptional arguments:\r\n');
console.log(' --user [username] The Intel AMT login username, admin is default.');
console.log(' --tls Specifies that TLS must be used.');
console.log(' --ipsync [0 or 1] Change the wired IPSync setting on Intel AMT 7+');
console.log(' --dhcp Change IPv4 wired interface to DHCP mode');
console.log(' --static Change IPv4 wired interface to static IP mode');
console.log(' --ip [1.2.3.4] Static IPv4 address (required)');
console.log(' --subnet [1.2.3.4] Static IPv4 subnet mask');
console.log(' --gateway [1.2.3.4] Static IPv4 default gateway');
console.log(' --dns [1.2.3.4] Primary DNS IPv4 address');
console.log(' --dns2 [1.2.3.4] Secondary DNS IPv4 address');
} else if (action == 'amtfeatures') {
console.log('AmtFeatures is used to get/set Intel AMT feature configuration. Example usage:\r\n\r\n meshcmd amtfeatures --host 1.2.3.4 --user admin --pass mypassword --tls --redir 1');
console.log('\r\nRequired arguments:\r\n');
console.log(' --host [hostname] The IP address or DNS name of Intel AMT, 127.0.0.1 is default.');
console.log(' --pass [password] The Intel AMT login password.');
console.log('\r\nOptional arguments:\r\n');
console.log(' --user [username] The Intel AMT login username, admin is default.');
console.log(' --tls Specifies that TLS must be used.');
console.log(' --consent [none/kvm/all] Set Intel AMT user consent feature.');
console.log(' --redir [0/1] Set Intel AMT redirection port feature.');
console.log(' --kvm [0/1] Set Intel AMT KVM feature.');
console.log(' --sol [0/1] Set Intel AMT Serial-over-LAN feature.');
console.log(' --ider [0/1] Set Intel AMT IDE redirection feature.');
} else if (action == 'meshcommander') {
console.log('This action launched a local web server that hosts MeshCommander, a Intel AMT management console.');
console.log('\r\nPossible arguments:\r\n');
console.log(' --localport [port] Local port used for the web server, 3000 is default.');
console.log('\r\nRun as a background service:\r\n');
console.log(' meshcommander install/uninstall/start/stop.');
} else if (action == 'amteventlog') {
console.log('AmtEventLog action will fetch the local or remote event log. Example usage:\r\n\r\n meshcmd amteventlog --host 1.2.3.4 --user admin --pass mypassword --tls --output events.txt');
console.log('\r\nPossible arguments:\r\n');
console.log(' --output [filename] The output file for the Intel AMT event log.');
console.log(' --host [hostname] The IP address or DNS name of Intel AMT, 127.0.0.1 is default.');
console.log(' --user [username] The Intel AMT login username, admin is default.');
console.log(' --pass [password] The Intel AMT login password.');
console.log(' --tls Specifies that TLS must be used.');
console.log(' --uuidoutput Output with unique identifier as the filename.');
console.log(' --json Output as a JSON format.');
} else if (action == 'amtauditlog') {
console.log('AmtAuditLog action will fetch the local or remote audit log. If used localy, no username/password is required. Example usage:\r\n\r\n meshcmd amtauditlog --host 1.2.3.4 --user admin --pass mypassword --tls --output audit.json');
console.log('\r\nPossible arguments:\r\n');
console.log(' --output [filename] The output file for the Intel AMT audit log.');
console.log(' --host [hostname] The IP address or DNS name of Intel AMT, 127.0.0.1 is default.');
console.log(' --user [username] The Intel AMT login username, admin is default.');
console.log(' --pass [password] The Intel AMT login password.');
console.log(' --tls Specifies that TLS must be used.');
console.log(' --uuidoutput Output with unique identifier as the filename.');
console.log(' --json Output as a JSON format.');
} else if (action == 'amtider') {
console.log('AmtIDER will mount a local disk images to a remote Intel AMT computer. Example usage:\r\n\r\n meshcmd amtider --host 1.2.3.4 --user admin --pass mypassword --tls --floppy disk.img --cdrom disk.iso');
console.log('\r\nPossible arguments:\r\n');
console.log(' --host [hostname] The IP address or DNS name of Intel AMT.');
console.log(' --user [username] The Intel AMT login username, admin is default.');
console.log(' --pass [password] The Intel AMT login password.');
console.log(' --tls Specifies that TLS must be used.');
console.log(' --floppy [file] Specifies .img file to be mounted as a flppy disk.');
console.log(' --cdrom [file] Specifies .img file to be mounted as a CDROM disk.');
console.log(' --timeout [seconds] Optional, disconnect after number of seconds without disk read.');
console.log(' --iderstart [onreboot|graceful|now] Optional, when to start the IDER session.');
} else if (action == 'amtscan') {
console.log('AmtSCAN will look for Intel AMT device on the network. Example usage:\r\n\r\n meshcmd amtscan --scan 192.168.1.0/24');
console.log('\r\Required arguments:\r\n');
console.log(' --scan [ip range] The IP address range to perform the scan on.');
} else if (action == 'amtwifi') {
console.log('AmtWifi is used to get/set Intel AMT Wifi configuration. Example usage:\r\n\r\n meshcmd amtwifi --host 1.2.3.4 --user admin --pass mypassword --list');
console.log('\r\nRequired arguments:\r\n');
console.log(' --host [hostname] The IP address or DNS name of Intel AMT, 127.0.0.1 is default.');
console.log(' --pass [password] The Intel AMT login password.');
console.log(' --[action] Action options are list, add, del.');
console.log('\r\nOptional arguments:\r\n');
console.log(' --user [username] The Intel AMT login username, admin is default.');
console.log(' --tls Specifies that TLS must be used.');
console.log(' --list List Wifi profiles');
console.log(' --add Add new Wifi profile');
console.log(' --name New Wifi profile name');
console.log(' --priority Priority of this profile - default 0');
console.log(' --ssid Wifi SSID');
console.log(' --auth Wifi Authentication method (4 - WPA, 6 - WPA2/RSN) - default 6');
console.log(' --enc Wifi Encryption type (3 - TKIP, 4 - CCMP) - default 3');
console.log(' --psk Wifi password/pre-shared key');
console.log(' --del [profile-name] Delete new Wifi profile');
} else if (action == 'amtwake') {
console.log('AmtWake is used to view/set/remote Intel AMT Wake Alarms. Example usage:\r\n\r\n meshcmd amtwake --host 1.2.3.4 --user admin --pass mypassword --list');
console.log('\r\nRequired arguments:\r\n');
console.log(' --host [hostname] The IP address or DNS name of Intel AMT, 127.0.0.1 is default.');
console.log(' --pass [password] The Intel AMT login password.');
console.log(' --[action] Action options are list, add, del.');
console.log('\r\nOptional arguments:\r\n');
console.log(' --user [username] The Intel AMT login username, admin is default.');
console.log(' --tls Specifies that TLS must be used.');
console.log(' --list List wake alarms profile');
console.log(' --add [alarm-name] Add new wake alarm');
console.log(' --date [yyyy-mm-dd] Alarm date in year-month-day format');
console.log(' --time (hh:mm:ss) Optional alarm time in hours:minutes:seconds format, default is 00:00:00.');
console.log(' --interval (dd-hh-mm) Optional alarm interval in days-hours-minutes format, default is alarm once.');
console.log(' --deletewhendone Indicates alarm is removed once triggered, default is to no remove.');
console.log(' --del [alarm-name] Remove a wake alarm');
} else if (action == 'amtrpe') {
console.log('AmtRPE is used to erase some elements of a remote Intel AMT platform. Example usage:\r\n\r\n meshcmd amtrpe --host 1.2.3.4 --user admin --pass mypassword');
console.log('\r\nRequired arguments:\r\n');
console.log(' --host [hostname] The IP address or DNS name of Intel AMT, 127.0.0.1 is default.');
console.log(' --pass [password] The Intel AMT login password.');
console.log('\r\nOptional arguments:\r\n');
console.log(' --user [username] The Intel AMT login username, admin is default.');
console.log(' --tls Specifies that TLS must be used.');
console.log(' --reset / --poweron Power action to perform on Intel AMT device.');
console.log(' --pyrite [PSID] Perform pyrite revert.');
console.log(' --ssd [Password] Perform secure erase all SSDs.');
console.log(' --tpm Perform TPM Clear.');
console.log(' --nvm Perform clear BIOS NVM variables.');
console.log(' --bios Perform BIOS reload of golden configuration.');
console.log(' --csme Perform CSME unconfigure.');
} else if (action == 'amtddns') {
console.log('AmtDDNS is used to query and set the Intel AMT dynamic DNS settings. Example usage:\r\n\r\n meshcmd amtddns --host 1.2.3.4 --user admin --pass mypassword');
console.log('\r\nRequired arguments:\r\n');
console.log(' --host [hostname] The IP address or DNS name of Intel AMT, 127.0.0.1 is default.');
console.log(' --pass [password] The Intel AMT login password.');
console.log('\r\nOptional arguments:\r\n');
console.log(' --set [disabled/dhcp/enabled] Set the dynamic DNS mode.');
console.log(' --interval [minutes] Set update interval in minutes, default is 1440, minimum is 20.');
console.log(' --ttl [seconds] Set time to live, default is 900.');
} else {
actions.shift();
console.log('Invalid action, usage:\r\n\r\n meshcmd help [action]\r\n\r\nValid actions are: ' + actions.join(', ') + '.');
}
2021-07-16 21:43:30 -04:00
exit(0); return;
}
settings.action = settings.action.toLowerCase();
debug(1, "Settings: " + JSON.stringify(settings));
// Setup the proxy if needed
if ((typeof settings.proxy) == 'string') {
var proxy = settings.proxy.split(':'), proxyport = (proxy.length == 2) ? parseInt(proxy[1]) : 0;
if ((proxy.length != 2) || (proxy[0].length < 1) || (proxyport < 1) || (proxyport > 65535)) { console.log('Invalid \"proxy\" specified, use --proxy [hostname]:[port].'); exit(1); return; }
try { require('global-tunnel').initialize({ host: proxy[0], port: proxyport }); } catch (ex) { console.log(ex); exit(1); return; }
console.log('Proxy set to ' + proxy[0] + ':' + proxyport);
}
if (settings.action == 'amtstartconfig') {
// Start Intel AMT configuration
var amtMeiModule, amtMei;
try { amtMeiModule = require('amt-mei'); amtMei = new amtMeiModule(); } catch (ex) { console.log(ex); exit(1); return; }
2021-10-26 02:12:55 -04:00
amtMei.on('error', function (e) { console.log('amtstartconfig error: ' + e); exit(1); return; });
amtMei.startConfiguration(function (state) {
if (state == 3) { console.log("Intel AMT is not in correct mode."); }
else if (state == 1) { console.log("Intel AMT internal error."); }
else if (state == 48) { console.log("Random generator not ready."); }
else if (state == 49) { console.log("Certificate not ready."); }
else if (state == 0) { console.log("Success."); }
else { console.log("Unknown status: " + state); }
2021-07-16 21:43:30 -04:00
exit(state);
});
} else if (settings.action == 'amtstopconfig') {
// Stop Intel AMT configuration
var amtMeiModule, amtMei;
try { amtMeiModule = require('amt-mei'); amtMei = new amtMeiModule(); } catch (ex) { console.log(ex); exit(1); return; }
2021-10-26 02:12:55 -04:00
amtMei.on('error', function (e) { console.log('amtstopconfig error: ' + e); exit(1); return; });
amtMei.stopConfiguration(function (state) {
if (state == 3) { console.log("Intel AMT is not in in-provisionning mode."); }
else if (state == 1) { console.log("Intel AMT internal error."); }
else if (state == 0) { console.log("Success."); }
else { console.log("Unknown status: " + state); }
2021-07-16 21:43:30 -04:00
exit(state);
});
} else if (settings.action == 'smbios') {
// Display SM BIOS tables in raw form
SMBiosTables = require('smbios');
SMBiosTables.get(function (data) {
var r = SMBiosTables.parse(data);
2021-07-16 21:43:30 -04:00
var out = JSON.stringify(r, null, 2);
if (settings.output == null) { console.log(out); } else { var file = fs.openSync(settings.output, 'w'); fs.writeSync(file, Buffer.from(out, 'utf8')); fs.closeSync(file); }
2021-07-16 21:43:30 -04:00
exit(0);
});
} else if (settings.action == 'rawsmbios') {
// Display SM BIOS tables in raw form
SMBiosTables = require('smbios');
SMBiosTables.get(function (data) {
var out = '';
for (var i in data) { var header = false; for (var j in data[i]) { if (data[i][j].length > 0) { if (header == false) { out += ('Table type #' + i + ((SMBiosTables.smTableTypes[i] == null) ? '' : (', ' + SMBiosTables.smTableTypes[i]))) + '\r\n'; header = true; } out += (' ' + data[i][j].toString('hex')) + '\r\n'; } } }
if (settings.output == null) { console.log(out); } else { var file = fs.openSync(settings.output, 'w'); fs.writeSync(file, Buffer.from(out, 'utf8')); fs.closeSync(file); }
2021-07-16 21:43:30 -04:00
exit(0);
});
} else if (settings.action == 'route') {
// MeshCentral Router, port map local TCP port to a remote computer
if ((settings.localport == null) || (typeof settings.localport != 'number') || (settings.localport < 0) || (settings.localport > 65535)) { console.log('No or invalid \"localPort\" specified, use --localport [localport].'); exit(1); return; }
if ((settings.remotenodeid == null) || (typeof settings.remotenodeid != 'string')) { console.log('No or invalid \"remoteNodeId\" specified.'); exit(1); return; }
if (((settings.username == null) || (typeof settings.username != 'string') || (settings.username == '')) && (settings.authcookie == null || typeof settings.authcookie != 'string' || settings.authcookie == '')) { console.log('No or invalid \"username\" specified, use --username [username].'); exit(1); return; }
if (((settings.password == null) || (typeof settings.password != 'string') || (settings.password == '')) && (settings.authcookie == null || typeof settings.authcookie != 'string' || settings.authcookie == '')) { console.log('No or invalid \"password\" specified, use --password [password].'); exit(1); return; }
2021-04-02 20:37:36 -04:00
if (settings.serverid != null) {
if ((typeof settings.serverid != 'string') || (settings.serverid.length != 96)) { console.log('No or invalid \"serverId\" specified.'); exit(1); return; }
} else {
if ((settings.serverhttpshash == null) || (typeof settings.serverhttpshash != 'string') || (settings.serverhttpshash.length != 96)) { console.log('No or invalid \"serverHttpsHash\" or \"serverId\" specified.'); exit(1); return; }
}
if ((settings.remoteport == null) || (typeof settings.remoteport != 'number') || (settings.remoteport < 0) || (settings.remoteport > 65535)) { console.log('No or invalid \"remotePort\" specified, use --remoteport [remoteport].'); exit(1); return; }
if (settings.serverurl != null) { startRouter(); } else { discoverMeshServer(); } // Start MeshCentral Router
} else if ((settings.action == 'amtversion') || (settings.action == 'amtversions') || (settings.action == 'amtver')) {
// Display Intel ME versions
var amtMeiModule, amtMei;
try { amtMeiModule = require('amt-mei'); amtMei = new amtMeiModule(); } catch (ex) { console.log(ex); exit(1); return; }
2021-10-26 02:12:55 -04:00
amtMei.on('error', function (e) { console.log('amtversion error: ' + e); exit(1); return; });
amtMei.getVersion(function (val) {
if (args.json) {
console.log(JSON.stringify(val, null, 2));
} else {
console.log("BIOS Version = " + val.BiosVersion.toString());
for (var version in val.Versions) {
var extras = '', skuBits = ['', 'iQST', 'ASF', 'AMT', 'ISM', 'TPM', '', '', 'HomeIT', '', 'WOX', '', '', 'AT-p', 'Corporate', 'L3 Mgt Upgrade'];
if (val.Versions[version].Description == 'Sku') {
var n = parseInt(val.Versions[version].Version), x = [], xx = 1;
for (var i = 0; i < skuBits.length; i++) { if ((n & xx) != 0) { x.push(skuBits[i]); } xx = xx << 1; }
if (x.length > 0) { extras = ' (' + x.join(', ') + ')' }
}
console.log(val.Versions[version].Description + " = " + val.Versions[version].Version + extras);
}
}
2021-07-16 21:43:30 -04:00
exit(0);
return;
});
} else if (settings.action == 'amthashes') {
// Display Intel AMT list of trusted hashes
2021-07-16 21:43:30 -04:00
var amtMeiModule, amtMei, amtHashes = [];
try { amtMeiModule = require('amt-mei'); amtMei = new amtMeiModule(); } catch (ex) { console.log(ex); exit(1); return; }
2021-10-26 02:12:55 -04:00
amtMei.on('error', function (e) { console.log('amthashes error: ' + e); exit(1); return; });
amtMei.getHashHandles(function (handles) {
exitOnCount = handles.length;
for (var i = 0; i < handles.length; ++i) {
this.getCertHashEntry(handles[i], function (result) {
2020-11-24 22:56:59 -05:00
var certState = [];
if (result.isDefault) { certState.push('Default'); }
if (result.isActive) { certState.push('Active'); } else { certState.push('Disabled'); }
2021-07-16 21:43:30 -04:00
amtHashes.push(result);
if (!args.json) { console.log(result.name + ', (' + certState.join(', ') + ')\r\n ' + result.hashAlgorithmStr + ': ' + result.certificateHash); }
if (--exitOnCount == 0) { if (args.json) { console.log(JSON.stringify(amtHashes, null, 2)); } exit(0); }
});
}
});
} else if (settings.action == 'netinfo') {
// Display network information
var interfaces = require('os').networkInterfaces();
console.log(JSON.stringify(interfaces, 2, ' '));
exit(0); return;
} else if (settings.action == 'amtinfo') {
// Display Intel AMT version and activation state
mestate = {};
var amtMeiModule, amtMei;
try { amtMeiModule = require('amt-mei'); amtMei = new amtMeiModule(); } catch (ex) { console.log(ex); exit(1); return; }
2021-10-26 02:12:55 -04:00
amtMei.on('error', function (e) { console.log('amtinfo error: ' + e); exit(1); return; });
2020-10-20 21:14:00 -04:00
try {
amtMei.getVersion(function (result) {
if (result) {
for (var version in result.Versions) {
if (result.Versions[version].Description == 'AMT') { mestate.ver = result.Versions[version].Version; }
if (result.Versions[version].Description == 'Sku') { mestate.sku = parseInt(result.Versions[version].Version); }
}
amtMei.getProvisioningState(function (result) { if (result) { mestate.ProvisioningState = result; } });
amtMei.getProvisioningMode(function (result) { if (result) { mestate.ProvisioningMode = result; } });
amtMei.getEHBCState(function (result) { mestate.ehbc = ((result === true) || (typeof result == 'object') && (result.EHBC === true)); });
amtMei.getControlMode(function (result) { if (result) { mestate.controlmode = result; } });
amtMei.getMACAddresses(function (result) { if (result) { mestate.mac = result; } });
amtMei.getLanInterfaceSettings(0, function (result) { if (result) { mestate.net0 = result; } });
amtMei.getLanInterfaceSettings(1, function (result) { if (result) { mestate.net1 = result; } });
amtMei.getUuid(function (result) { if ((result != null) && (result.uuid != null)) { mestate.uuid = result.uuid; } });
amtMei.getRemoteAccessConnectionStatus(function (result) { if ((result != null) && (result.status == 0)) { mestate.networkStatus = result.networkStatus; mestate.remoteAccessStatus = result.remoteAccessStatus; mestate.remoteAccessTrigger = result.remoteAccessTrigger; mestate.mpsHostname = result.mpsHostname; } });
amtMei.getDnsSuffix(function (result) {
if (result) { mestate.DnsSuffix = result; }
2021-07-24 13:12:21 -04:00
getAmtOsDnsSuffix(mestate, function() {
if (args.json) {
console.log(JSON.stringify(mestate, null, 2));
exit(0);
2021-07-24 13:12:21 -04:00
} else if (mestate.ver && mestate.ProvisioningState && mestate.ProvisioningMode) {
var str = 'Intel ME v' + mestate.ver;
if (mestate.sku & 8) { str = 'Intel AMT v' + mestate.ver }
else if (mestate.sku & 16) { str = 'Intel SM v' + mestate.ver }
if (mestate.ProvisioningState.stateStr == 'PRE') { str += ', pre-provisioning state'; }
else if (mestate.ProvisioningState.stateStr == 'IN') { str += ', in-provisioning state'; }
else if (mestate.ProvisioningState.stateStr == 'POST') {
if (mestate.ProvisioningMode) {
if (mestate.controlmode) {
if (mestate.ProvisioningMode.modeStr == 'ENTERPRISE') { str += ', activated in ' + ["none", "Client Control Mode (CCM)", "Admin Control Mode (ACM)", "remote assistance mode"][mestate.controlmode.controlMode]; } else { str += ', activated in ' + mestate.ProvisioningMode.modeStr; }
} else {
str += ', activated in ' + mestate.ProvisioningMode.modeStr;
}
}
}
2021-07-24 13:12:21 -04:00
if (mestate.ehbc) { str += ', EHBC enabled'; }
str += '.';
if (mestate.net0 != null) { str += '\r\nWired ' + ((mestate.net0.enabled == 1) ? 'Enabled' : 'Disabled') + ((mestate.net0.dhcpEnabled == 1) ? ', DHCP' : ', Static') + ', ' + mestate.net0.mac + (mestate.net0.address == '0.0.0.0' ? '' : (', ' + mestate.net0.address)); }
if (mestate.net1 != null) { str += '\r\nWireless ' + ((mestate.net1.enabled == 1) ? 'Enabled' : 'Disabled') + ((mestate.net1.dhcpEnabled == 1) ? ', DHCP' : ', Static') + ', ' + mestate.net1.mac + (mestate.net1.address == '0.0.0.0' ? '' : (', ' + mestate.net1.address)); }
if ((mestate.net0 != null) && (mestate.net0.enabled == 1)) {
if (mestate.DnsSuffix != null) {
// Intel AMT has a trusted DNS suffix set, use that one.
str += '\r\nTrusted DNS suffix: ' + mestate.DnsSuffix;
} else if (mestate.OsDnsSuffix != null) {
// Already found the DNS suffix for the wired interface
str += '\r\nDNS suffix: ' + mestate.OsDnsSuffix;
} else {
// Look for the DNS suffix for the Intel AMT Ethernet interface
var fqdn = null, interfaces = require('os').networkInterfaces();
for (var i in interfaces) {
for (var j in interfaces[i]) {
if ((interfaces[i][j].mac == mestate.net0.mac) && (interfaces[i][j].fqdn != null) && (interfaces[i][j].fqdn != '')) { fqdn = interfaces[i][j].fqdn; }
}
}
2021-07-24 13:12:21 -04:00
if (fqdn != null) { str += '\r\nDNS suffix: ' + fqdn; }
}
2020-10-20 21:14:00 -04:00
}
2021-07-24 13:12:21 -04:00
if (typeof mestate.networkStatus == 'number') {
str += '\r\nConnection Status: ' + ['Direct', 'VPN', 'Outside', 'Unknown'][mestate.networkStatus];
str += ', CIRA: ' + ['Disconnected', 'Connecting', 'Connected'][mestate.remoteAccessStatus];
if ((mestate.remoteAccessStatus > 0) && (mestate.mpsHostname != null) && (mestate.mpsHostname.length > 0)) {
str += ' to ' + mestate.mpsHostname + ', ' + ['User initiated', 'Alert', 'Periodic', 'Provisioning'][mestate.remoteAccessTrigger];
}
}
2021-07-24 13:12:21 -04:00
console.log(str + '.');
exit(0);
} else {
console.log('Intel(R) AMT not supported.');
exit(1);
}
2021-07-24 13:12:21 -04:00
});
});
2020-10-20 21:14:00 -04:00
} else {
console.log("Unable to perform MEI operations, try running as " + ((process.platform == 'win32')?"administrator.":"root."));
exit(1); return;
}
2020-10-20 21:14:00 -04:00
});
} catch (ex) { console.log("Unable to perform MEI operations, try running as " + ((process.platform == 'win32')?"administrator.":"root.")); exit(1); return; }
} else if (settings.action == 'amtinfojson') {
// Display Intel AMT version and activation state
getMeiState(15, function (state) { // Flags: 1 = Versions, 2 = OsAdmin, 4 = Hashes, 8 = Network
if (typeof args.post == 'string') {
console.log("Attempting to send to " + args.post);
var http = require('http');
var options = http.parseUri(args.post);
options.method = 'POST';
options.rejectUnauthorized = false;
options.checkServerIdentity = function (cert) { }
//console.log("options: " + JSON.stringify(options, null, 2));
var req = http.request(options);
2021-10-26 02:12:55 -04:00
req.on('error', function (e) { console.log("amtinfojson error: " + e); exit(1); });
req.on('response', function (response) { console.log("Status code: " + response.statusCode); exit(1); });
req.end(JSON.stringify(state));
} else {
console.log(JSON.stringify(state, null, 2)); exit(0);
}
});
} else if (settings.action == 'amtsavestate') {
// Save the entire state of Intel AMT info a JSON file
if ((settings.password == null) || (typeof settings.password != 'string') || (settings.password == '')) { console.log('No or invalid \"password\" specified, use --password [password].'); exit(1); return; }
if ((settings.hostname == null) || (typeof settings.hostname != 'string') || (settings.hostname == '')) { settings.hostname = '127.0.0.1'; }
if ((settings.username == null) || (typeof settings.username != 'string') || (settings.username == '')) { settings.username = 'admin'; }
if ((settings.output == null) || (typeof settings.output != 'string') || (settings.output == '')) { console.log('No or invalid \"output\" file specified, use --output [filename].'); exit(1); return; }
settings.protocol = 'http:';
settings.localport = 16992;
debug(1, "Settings: " + JSON.stringify(settings));
saveEntireAmtState();
} else if ((settings.action == 'microlms') || (settings.action == 'amtlms') || (settings.action == 'lms')) {
// Start Intel AMT MicroLMS
// Because of a bug in MEI on Linux, LMS will jam if not root. To work around this, start by checking AMT state first.
getMeiState(0, function (xstate) { // Flags: 1 = Versions, 2 = OsAdmin, 4 = Hashes, 8 = Network
if (xstate == null) { console.log("Unable to get Intel AMT state, try running as " + ((process.platform == 'win32')?"administrator.":"root.")); exit(1); return; }
startLms(function (state) {
console.log(['MicroLMS did not start. Must run as administrator or LMS already active.', 'MicroLMS started.', 'MicroLMS started, MeshCommander on HTTP/16994.', 'MEI error'][state]);
if (((state == 0) || (state == 3)) && (settings.noconsole === true)) { exit(0); } else { console.log('Press ctrl-c to exit.'); }
}, false, xstate);
});
} else if (settings.action == 'amtpresence') {
// Heartbeat a Intel AMT watchdog
if ((settings.password == null) || (typeof settings.password != 'string') || (settings.password == '')) { console.log('No or invalid \"password\" specified, use --password [password].'); exit(1); return; }
if ((settings.username == null) || (typeof settings.username != 'string') || (settings.username == '')) { settings.username = 'admin'; }
if ((settings.agent == null) || (typeof settings.agent != 'string') || (settings.agent == '')) { console.log('No or invalid \"agent\" specified, use --agent [agent].'); exit(1); return; }
performAmtAgentPresence();
} else if (settings.action == 'amtuuid') {
// Start running
2021-11-02 13:34:32 -04:00
if (settings.hostname != null)
{
if ((settings.password == null) || (typeof settings.password != 'string') || (settings.password == '')) { console.log('No or invalid \"password\" specified, use --password [password].'); exit(1); return; }
if ((settings.username == null) || (typeof settings.username != 'string') || (settings.username == '')) { settings.username = 'admin'; }
}
settings.protocol = 'http:';
settings.localport = 16992;
debug(1, "Settings: " + JSON.stringify(settings));
getAmtUuid();
} else if (settings.action == 'amtconfig') {
// Start Intel AMT configuration
if ((settings.url == null) || (typeof settings.url != 'string') || (settings.url == '')) { console.log('No MeshCentral server URL specified, use --url [url].'); exit(1); return; }
if ((settings.id == null) || (typeof settings.id != 'string') || (settings.id == '')) { console.log('No device group identifier specified, use --id [identifier].'); exit(1); return; }
settings.id = settings.id.replace('\'', ''); // Remove single quote.
debug(1, "Settings: " + JSON.stringify(settings));
configureAmt();
} else if (settings.action == 'amtccm') {
// Start activation to CCM
if (((settings.password == null) || (typeof settings.password != 'string') || (settings.password == ''))) { console.log('No or invalid parameters specified, use --password [password] or --url [url].'); exit(1); return; }
settings.protocol = 'http:';
settings.localport = 16992;
debug(1, "Settings: " + JSON.stringify(settings));
activeToCCM();
} else if (settings.action == 'amtdeactivate') {
// Deactivate CCM
debug(1, "Settings: " + JSON.stringify(settings));
deactivateCCM();
} else if (settings.action == 'amtacmdeactivate') {
// Deactivate ACM
if ((settings.password == null) || (typeof settings.password != 'string') || (settings.password == '')) { console.log('No or invalid \"password\" specified, use --password [password].'); exit(1); return; }
if ((settings.type == null) || (typeof settings.type != 'string') || (settings.type == '')) { console.log('Unprovisioning \"type\" must be specified, use --type [partial/full].'); exit(1); return; }
if ((settings.username == null) || (typeof settings.username != 'string') || (settings.username == '')) { settings.username = 'admin'; }
if (settings.hostname == null) { settings.hostname = '127.0.0.1'; }
if (settings.tls == null) { settings.tls = false; }
debug(1, "Settings: " + JSON.stringify(settings));
deactivateACM();
} else if (settings.action == 'meshcommander') { // Start MeshCommander
startMeshCommander();
//} else if (settings.action == 'amtdisable') { // Disable AMT Network Interface
// amtDisable();
} else if (settings.action == 'amtscan') {
// Scan the network for Intel AMT devices
if ((settings.scan == null) || (typeof settings.scan != 'string') || (settings.scan == '')) { console.log('No or invalid \"scan\" specified, use --scan [ip range].'); exit(1); return; }
console.log('Scanning: ' + settings.scan + '...');
var AMTScannerModule = require('amt-scanner');
var amtscanner = new AMTScannerModule(), r = '';
amtscanner.scan(settings.scan, 2000, function (data) {
if (data.length > 0) {
r = '', pstates = ['NotActivated', 'InActivation', 'Activated'];
for (var i in data) {
var x = data[i];
if (r != '') { r += '\r\n'; }
r += x.address + ' - Intel AMT v' + x.majorVersion + '.' + x.minorVersion;
if (x.provisioningState < 3) { r += (', ' + pstates[x.provisioningState]); }
if (x.provisioningState == 2) { r += (', ' + x.openPorts.join(', ')); }
r += '.';
}
} else {
r = 'No Intel AMT found.';
}
console.log(r);
2021-07-16 21:43:30 -04:00
exit(0);
});
} else if (settings.action == 'amtauditlog') { // Read the Intel AMT audit log
if (settings.hostname != null) {
if ((settings.password == null) || (typeof settings.password != 'string') || (settings.password == '')) { console.log('No or invalid \"password\" specified, use --password [password].'); exit(1); return; }
if ((settings.username == null) || (typeof settings.username != 'string') || (settings.username == '')) { settings.username = 'admin'; }
} else { settings.hostname = '127.0.0.1'; }
readAmtAuditLog();
} else if (settings.action == 'amteventlog') { // Read the Intel AMT audit log
if (settings.hostname != null) {
if ((settings.password == null) || (typeof settings.password != 'string') || (settings.password == '')) { console.log('No or invalid \"password\" specified, use --password [password].'); exit(1); return; }
if ((settings.username == null) || (typeof settings.username != 'string') || (settings.username == '')) { settings.username = 'admin'; }
} else { settings.hostname = '127.0.0.1'; }
readAmtEventLog();
} else if (settings.action == 'amtider') { // Remote mount IDER image
if ((settings.hostname == null) || (typeof settings.hostname != 'string') || (settings.hostname == '')) { console.log('No or invalid \"hostname\" specified, use --hostname [password].'); exit(1); return; }
if ((settings.password == null) || (typeof settings.password != 'string') || (settings.password == '')) { console.log('No or invalid \"password\" specified, use --password [password].'); exit(1); return; }
if ((settings.username == null) || (typeof settings.username != 'string') || (settings.username == '')) { settings.username = 'admin'; }
if ((settings.floppy == null) || (typeof settings.floppy != 'string') || (settings.floppy == '')) { settings.floppy = null; }
if ((settings.cdrom == null) || (typeof settings.cdrom != 'string') || (settings.cdrom == '')) { settings.cdrom = null; }
if ((settings.floppy == null) && (settings.cdrom == null)) { console.log('No or invalid \"floppy\" or \"cdrom\" specified, use --floppy [file] or --cdrom [file].'); exit(1); return; }
performIder();
} else if (settings.action == 'amtnetwork') { // Perform remote Intel AMT wired IPv4 configuration operation
if (settings.hostname == null) { settings.hostname = '127.0.0.1'; }
if ((settings.password == null) || (typeof settings.password != 'string') || (settings.password == '')) { console.log('No or invalid \"password\" specified, use --password [password].'); exit(1); return; }
if ((settings.username == null) || (typeof settings.username != 'string') || (settings.username == '')) { settings.username = 'admin'; }
performAmtNetConfig(args);
} else if (settings.action == 'amtwifi') { // Perform remote Intel AMT Wifi configuration operation
if (settings.hostname == null) { settings.hostname = '127.0.0.1'; }
if ((settings.password == null) || (typeof settings.password != 'string') || (settings.password == '')) { console.log('No or invalid \"password\" specified, use --password [password].'); exit(1); return; }
if ((settings.username == null) || (typeof settings.username != 'string') || (settings.username == '')) { settings.username = 'admin'; }
if (args.add != null) {
if ((args.name == null) || (typeof args.name != 'string') || args.name == '') { console.log("Wifi profile name is required."); exit(1); return; }
if ((args.ssid == null) || (typeof args.ssid != 'string') || args.ssid == '') { console.log("Wifi SSID is required."); exit(1); return; }
if ((args.psk == null) || (typeof args.psk != 'string') || args.psk == '') { console.log("Wifi password is required."); exit(1); return; }
}
if (args.del != null) {
if ((settings.name == null) || (typeof settings.name != 'string') || settings.name == '') { console.log("Wifi profile name is required."); exit(1); return; }
}
performAmtWifiConfig(args);
} else if (settings.action == 'amtwake') { // Perform remote Intel AMT wake alarm operations
if (settings.hostname == null) { settings.hostname = '127.0.0.1'; }
if ((settings.password == null) || (typeof settings.password != 'string') || (settings.password == '')) { console.log('No or invalid \"password\" specified, use --password [password].'); exit(1); return; }
if ((settings.username == null) || (typeof settings.username != 'string') || (settings.username == '')) { settings.username = 'admin'; }
if ((args.del != null) && ((typeof args.del != 'string') || args.del == '')) { console.log("Alarm name is required (--del [name])."); exit(1); return; }
if (args.add != null) {
if (((typeof args.add != 'string') || args.add == '')) { console.log("Wake alarm name is required (--add [name])."); exit(1); return; }
if (((typeof args.date != 'string') || args.data == '')) { console.log("Wake alarm date is required (--date [yyyy-mm-dd])."); exit(1); return; }
}
performAmtWakeConfig(args);
} else if (settings.action == 'amtrpe') { // Perform Intel AMT remote platform erase operations
if (settings.hostname == null) { settings.hostname = '127.0.0.1'; }
if ((settings.password == null) || (typeof settings.password != 'string') || (settings.password == '')) { console.log('No or invalid \"password\" specified, use --password [password].'); exit(1); return; }
if ((settings.username == null) || (typeof settings.username != 'string') || (settings.username == '')) { settings.username = 'admin'; }
performAmtPlatformErase(args);
} else if (settings.action == 'amtddns') { // Perform Intel AMT dynamic DNS get/set
if (settings.hostname == null) { settings.hostname = '127.0.0.1'; }
if ((settings.password == null) || (typeof settings.password != 'string') || (settings.password == '')) { console.log('No or invalid \"password\" specified, use --password [password].'); exit(1); return; }
if ((settings.username == null) || (typeof settings.username != 'string') || (settings.username == '')) { settings.username = 'admin'; }
if (args.set != null) { args.set = args.set.toLowerCase(); }
if ((args.set != null) && (args.set != 'enabled') && (args.set != 'dhcp') && (args.set != 'disabled')) { console.log('Intel AMT DDNS can only bet set to "enabled", "dhcp" or "disabled".'); }
if (args.interval != null) { args.interval = parseInt(args.interval); if ((typeof args.interval != 'number') || (isNaN(args.interval))) { console.log('Interval must be a number.'); exit(1); return; } if (args.interval < 20) { console.log('Interval must be at least 20 minutes.'); exit(1); return; } }
if (args.ttl != null) { args.ttl = parseInt(args.ttl); if ((typeof args.ttl != 'number') || (isNaN(args.ttl))) { console.log('TTL must be a number.'); exit(1); return; } }
performAmtDynamicDNS(args);
} else if (settings.action == 'amtfeatures') { // Perform remote Intel AMT feature configuration operation
if (settings.hostname == null) { settings.hostname = '127.0.0.1'; }
if ((settings.password == null) || (typeof settings.password != 'string') || (settings.password == '')) { console.log('No or invalid \"password\" specified, use --password [password].'); exit(1); return; }
if ((settings.username == null) || (typeof settings.username != 'string') || (settings.username == '')) { settings.username = 'admin'; }
performAmtFeatureConfig(args);
} else if (settings.action == 'amtpower') { // Perform remote Intel AMT power operation
if ((settings.hostname == null) || (typeof settings.hostname != 'string') || (settings.hostname == '')) { console.log('No or invalid \"hostname\" specified, use --hostname [host].'); exit(1); return; }
if ((settings.password == null) || (typeof settings.password != 'string') || (settings.password == '')) { console.log('No or invalid \"password\" specified, use --password [password].'); exit(1); return; }
if ((settings.username == null) || (typeof settings.username != 'string') || (settings.username == '')) { settings.username = 'admin'; }
/*
2 = Power On
3 = Sleep - Light
4 = Sleep - Deep
5 = Power Cycle (Off Soft)
6 = Power Off - Hard
7 = Hibernate
8 = Power Off - Soft
9 = Power Cycle (Off Hard)
2020-06-15 19:37:02 -04:00
10 = Main Bus Reset
11 = Diagnostic Interrupt (NMI)
12 = Power Off - Soft Graceful
13 = Power Off - Hard Graceful
2020-06-15 19:37:02 -04:00
14 = Main Bus Reset Graceful
15 = Power Cycle (Off - Soft Graceful)
16 = Power Cycle (Off - Hard Graceful)
*/
settings.poweraction = 0;
if (args.poweron) { settings.poweraction = 2; }
if (args.sleep) { settings.poweraction = 3; }
if (args.powercycle) { settings.poweraction = 5; }
if (args.poweroff) { settings.poweraction = 8; }
if (args.hibernate) { settings.poweraction = 7; }
if (args.reset) { settings.poweraction = 10; }
//if (settings.poweraction == 0) { console.log('No power action, specify --poweron, --sleep, --powercycle, --poweroff, --hibernate, --reset.'); exit(1); return; }
// Accepted option for boot device are: pxe, hdd, cd
var bootdevices = ['pxe','hdd','cd'];
var ider_bootdevices = ['ider-floppy', 'ider-cdrom']
if (args.bootdevice) {
if (bootdevices.indexOf(args.bootdevice.toLowerCase())>=0) {
settings.bootdevice = args.bootdevice
2021-03-25 16:58:24 -04:00
// Set bootindex to 0 by default, unless overriden
settings.bootindex = 0
settings.ider_bootindex = 0
settings.ider_boot = false;
} else if (ider_bootdevices.indexOf(args.bootdevice.toLowerCase())>=0) {
settings.bootindex = 0
settings.ider_bootindex = ider_bootdevices.indexOf(args.bootdevice.toLowerCase());
settings.ider_boot = true;
} else {
console.log('Supported boot devices are pxe, hdd, cd, ider-floppy, ider-cdrom'); exit(1); return;
}
}
// boot index for cd and hdd
if (args.bootindex && args.bootindex >=0) {
settings.bootindex = args.bootindex;
}
performAmtPowerAction();
} else {
2021-03-25 16:58:24 -04:00
console.log('Invalid "action" specified.'); exit(1); return;
}
}
//
// Intel AMT Agent Presence
//
function performAmtAgentPresence() { startLms(function () { tempWatchdogTimer = setTimeout(performAmtAgentPresenceRegister, 3000); }); }
function performAmtAgentPresenceRegister() {
// Setup the Intel AMT WSMAN stack
tempWatchdogTimer = null;
var transport = require('amt-wsman-duk');
var wsman = require('amt-wsman');
var amt = require('amt');
wsstack = new wsman(transport, '127.0.0.1', settings.tls ? 16993 : 16992, settings.username, settings.password, settings.tls);
amtstack = new amt(wsstack);
// Register the watchdog
watchdog = { DeviceID: Buffer.from(guidToStr(settings.agent.split('-').join('')).split('-').join(''), 'hex').toString('base64'), Retry: 0 };
amtstack.AMT_AgentPresenceWatchdog_RegisterAgent(performAmtAgentPresenceRegisterRetry, watchdog, watchdog.Seq, { 'DeviceID': watchdog.DeviceID });
}
// Called after the agent is registered
function performAmtAgentPresenceRegisterRetry(stack, name, response, status, watchdog) {
if ((status == 200) && (response.Body.SessionSequenceNumber) && (response.Body.TimeoutInterval)) {
console.log('Asserting presence of the watchdog...');
watchdog.Seq = response.Body.SessionSequenceNumber;
watchdog.Interval = response.Body.TimeoutInterval * 800;
watchdog.Retry = 0;
tempWatchdogTimer = setTimeout(performAmtAgentPresenceAssert, watchdog.Interval);
} else {
debug(1, 'Failed to register, status = ' + status);
watchdog.Retry++;
if (watchdog.Retry < 5) {
tempWatchdogTimer = setTimeout(function () { amtstack.AMT_AgentPresenceWatchdog_RegisterAgent(performAmtAgentPresenceRegisterRetry, watchdog, watchdog.Seq, { 'DeviceID': watchdog.DeviceID }); }, 1000);
} else {
console.log('Failed to register this watchdog.');
exit(0);
}
}
}
// Start a new agent assert
function performAmtAgentPresenceAssert() {
watchdog.Seq++;
amtstack.AMT_AgentPresenceWatchdog_AssertPresence(watchdog.Seq, performAmtAgentPresenceAssertRetry, watchdog, 0, { 'DeviceID': watchdog.DeviceID });
}
// Called after the agent is asserted
function performAmtAgentPresenceAssertRetry(stack, name, response, status, watchdog) {
if (status == 200) {
debug(1, 'Successful assert, sequence = ' + watchdog.Seq);
watchdog.Retry = 0;
tempWatchdogTimer = setTimeout(performAmtAgentPresenceAssert, watchdog.Interval);
} else {
debug(1, 'Failed to assert, status = ' + status);
watchdog.Retry++;
if (watchdog.Retry < 5) {
amtstack.AMT_AgentPresenceWatchdog_AssertPresence(watchdog.Seq, performAmtAgentPresenceAssertRetry, watchdog, 0, { 'DeviceID': watchdog.DeviceID });
} else {
console.log('Failed to assert presence on this watchdog.');
exit(0);
}
}
}
function performAmtAgentPresenceEx5(stack, name, response, status, watchdog) {
console.log('b', status, watchdog);
if (status == 200) {
watchdog.Retry = 0;
} else {
watchdog.Retry++;
if (watchdog.Retry < 5) {
amtstack.AMT_AgentPresenceWatchdog_AssertPresence(watchdog.Seq, performAmtAgentPresenceEx4, watchdog, 0, { 'DeviceID': watchdog.DeviceID });
} else {
console.log('Failed to assert presence on this watchdog.');
exit(0);
}
}
}
//
// Intel AMT Event Log
//
function readAmtEventLog() {
// See if MicroLMS needs to be started
if ((settings.hostname == '127.0.0.1') || (settings.hostname.toLowerCase() == 'localhost')) {
settings.noconsole = true; startLms(readAmtEventLogEx);
} else {
readAmtEventLogEx(9999);
}
}
function readAmtEventLogEx(x) {
if (x == 9999) {
var transport = require('amt-wsman-duk');
var wsman = require('amt-wsman');
var amt = require('amt');
wsstack = new wsman(transport, settings.hostname, settings.tls ? 16993 : 16992, settings.username, settings.password, settings.tls);
amtstack = new amt(wsstack);
amtstack.GetMessageLog(readAmtEventLogEx2);
} else {
osamtstack.GetMessageLog(readAmtEventLogEx2);
}
}
function readAmtEventLogEx2(stack, messages) {
if (messages == null) {
console.log('Unable to get event log.');
} else {
var out = '';
if (settings.json) {
out = JSON.stringify(messages, 4, ' ');
} else {
for (var i in messages) { out += messages[i].Time + ', ' + messages[i].EntityStr + ', ' + messages[i].Desc + ', ' + messages[i].EventSeverity + '\r\n'; }
}
if ((settings.output == null || settings.output == "") && !settings.uuidoutput) { console.log(out); exit(1); }
else {
try {
if (settings.output) {
var file = fs.openSync(settings.output, 'w');
fs.writeSync(file, Buffer.from(out));
fs.closeSync(file);
2021-07-16 21:43:30 -04:00
exit(0);
}
else if (settings.uuidoutput) {
var destpath = null; //Dest path where messagelog file will be saved
if ((typeof settings.uuidoutput) == 'string') {
fs.statSync(settings.uuidoutput).isDirectory();//Validate directory path
destpath = settings.uuidoutput;
}
//Generate uuid and append it to dest path
stack.Get('CIM_ComputerSystemPackage', function (obj, name, response, xstatus, tag) {
if (xstatus == 200) {
var eventlogsfile = path.join(destpath, guidToStr(response.Body.PlatformGUID.toLowerCase() + '_Event' + (settings.json ? '.json' : '.csv')));
var file = fs.openSync(eventlogsfile, 'w');
fs.writeSync(file, Buffer.from(out));
fs.closeSync(file);
2021-07-16 21:43:30 -04:00
exit(0);
} else {
console.log('Intel AMT is not available or not activated, status = ' + status + '.');
2021-07-16 21:43:30 -04:00
exit(1);
}
});
}
else {
console.log('Invalid action, usage:\r\n\r\n meshcmd help amtauditlog');
exit(1);
}
}
catch (e) {
console.log(e);
exit(1);
}
}
}
}
//
// Intel AMT Audit Log
//
function readAmtAuditLog() {
// See if MicroLMS needs to be started
if ((settings.hostname == '127.0.0.1') || (settings.hostname.toLowerCase() == 'localhost')) {
settings.noconsole = true; startLms(readAmtAuditLogEx);
} else {
readAmtAuditLogEx(9999);
}
}
function readAmtAuditLogEx(x) {
if (x == 9999) {
var transport = require('amt-wsman-duk');
var wsman = require('amt-wsman');
var amt = require('amt');
wsstack = new wsman(transport, settings.hostname, settings.tls ? 16993 : 16992, settings.username, settings.password, settings.tls);
amtstack = new amt(wsstack);
amtstack.GetAuditLog(readAmtAuditLogEx2);
} else {
osamtstack.GetAuditLog(readAmtAuditLogEx2);
}
}
function readAmtAuditLogEx2(stack, response, status) {
if (status != 200) {
console.log('Unable to get audit log, status = ' + status + '.');
} else {
var out = '';
if (settings.json) {
out = JSON.stringify(response, 4, ' ');
} else {
for (var i in response) {
var name = ((response[i].Initiator != '') ? (response[i].Initiator + ': ') : '')
out += (response[i].Time + ' - ' + name + response[i].Event + '\r\n');
}
}
if ((settings.output == null || settings.output == "") && !settings.uuidoutput) { console.log(out); exit(1); }
else {
try {
if (settings.output) {
var file = fs.openSync(settings.output, 'w');
fs.writeSync(file, Buffer.from(out));
fs.closeSync(file);
2021-07-16 21:43:30 -04:00
exit(0);
}
else if (settings.uuidoutput) {
var destpath = null; //Dest path where auditlog file will be saved
if ((typeof settings.uuidoutput) == 'string') {
fs.statSync(settings.uuidoutput).isDirectory();//Validate directory path
destpath = settings.uuidoutput;
}
//Generate uuid and append it to dest path
stack.Get('CIM_ComputerSystemPackage', function (obj, name, response, xstatus, tag) {
if (xstatus == 200) {
var auditlogsfile = path.join(destpath, guidToStr(response.Body.PlatformGUID.toLowerCase() + '_Audit' + (settings.json ? '.json' : '.csv')));
var file = fs.openSync(auditlogsfile, 'w');
fs.writeSync(file, Buffer.from(out));
fs.closeSync(file);
2021-07-16 21:43:30 -04:00
exit(0);
} else {
console.log('Intel AMT is not available or not activated, status = ' + status + '.');
2021-07-16 21:43:30 -04:00
exit(1);
}
});
}
else {
console.log('Invalid action, usage:\r\n\r\n meshcmd help amtauditlog');
exit(1);
}
}
catch (e) {
console.log(e);
exit(1);
}
}
}
}
//
// Disable AMT Network
//
//function amtDisable() {
// settings.noconsole = true;
// startLms(amtDisableEx);
//}
//function amtDisableEx(stack, response, status) {
// //console.log(osamtstack);
// osamtstack.Get('AMT_EthernetPortSettings', function (stack, name, response, status) {
// console.log(response.Body);
// });
//}
//
// MeshCommander local web server
//
function startMeshCommander() {
if (settings.localport == null) { settings.localport = 3000; }
// Start the web server
var http = require('http');
webServer = http.createServer();
webServer.listen(settings.localport);
webServer.wsList = {};
webServer.wsListIndex = 0;
webServer.on('upgrade', function (req, socket, head) {
//console.log("WebSocket for " + req.url.split('?')[0]);
switch (req.url.split('?')[0]) {
case '/webrelay.ashx': // MeshCommander relay channel
var ws = socket.upgradeWebSocket();
socket.ws = ws;
ws.wsIndex = ++webServer.wsListIndex;
webServer.wsList[ws.wsIndex] = ws; // Keep a reference so the websocket and forwarder don't get disposed.
ws.pause();
// We got a new web socket connection, initiate a TCP connection to the target Intel AMT host/port.
var webargs = parseUrlArguments(req.url);
if (webargs.p) { webargs.p = parseInt(webargs.p); }
if (webargs.tls) { webargs.tls = parseInt(webargs.tls); }
if (webargs.tls1only) { webargs.tls1only = parseInt(webargs.tls1only); }
if (webargs.port) { webargs.port = parseInt(webargs.port); }
debug(1, 'Opening web socket connection to ' + webargs.host + ':' + webargs.port + '.');
//console.log('Opening web socket connection to ' + webargs.host + ':' + webargs.port + '.');
if (webargs.tls == 0) {
// If this is TCP (without TLS) set a normal TCP socket
var net = require('net');
ws.forwardclient = net.connect({ host: webargs.host, port: webargs.port })
ws.forwardclient.on('connect', function () { debug(1, 'Connected TCP to ' + webargs.host + ':' + webargs.port + '.'); this.pipe(this.ws, { end: false }); this.ws.pipe(this, { end: false }); });
ws.forwardclient.on('error', function () { debug(1, 'TCP connection error to ' + webargs.host + ':' + webargs.port + '.'); try { this.ws.end(); } catch (e) { } });
ws.forwardclient.ws = ws;
} else {
// If TLS is going to be used, setup a TLS socket
var tls = require('tls');
var tlsoptions = { host: webargs.host, port: webargs.port, rejectUnauthorized: false };
if (webargs.tls1only == 1) { tlsoptions.secureProtocol = 'TLSv1_method'; }
ws.forwardclient = tls.connect(tlsoptions, function () { debug(1, 'Connected TLS to ' + webargs.host + ':' + webargs.port + '.'); this.pipe(this.ws, { end: false }); this.ws.pipe(this, { end: false }); });
ws.forwardclient.on('error', function () { debug(1, 'TLS connection error to ' + webargs.host + ':' + webargs.port + '.'); try { this.ws.end(); } catch (e) { } });
ws.forwardclient.ws = ws;
}
// Handle pipe closure
ws.on('end', function () { debug(1, 'Disconnected from ' + webargs.host + ':' + webargs.port + '.'); try { this.forwardclient.end(); } catch (e) { } delete webServer.wsList[this.wsIndex]; });
ws.forwardclient.on('end', function () { try { this.ws.end(); } catch (e) { } });
break;
default:
socket.end();
break;
}
});
webServer.on('request', function (req, rsp) {
//console.log("WebRequest for " + req.url.split('?')[0]);
switch (req.url.split('?')[0]) {
case '/': // Serve MeshCommander Web Application
var meshcommander = null;
try { meshcommander = fs.readFileSync('meshcommander.htm'); } catch (e) { }
if (meshcommander != null) {
rsp.writeHead(200, 'OK', { Server: 'JSLMS', 'Cache-Control': 'max-age=0, no-cache', 'X-Frame-Options': 'DENY', 'Content-Type': 'text/html', 'Transfer-Encoding': 'chunked' });
rsp.end(meshcommander);
} else {
rsp.writeHead(200, 'OK', { Server: 'JSLMS', 'Cache-Control': 'max-age=0, no-cache', 'X-Frame-Options': 'DENY', 'Content-Type': 'text/html', 'Content-Encoding': 'gzip', 'Transfer-Encoding': 'chunked', ETag: FullSite_IntelAmtLocalWebApp_etag });
rsp.end(Buffer.from(FullSite_IntelAmtLocalWebApp, 'base64'));
}
break;
default: // Unknown request
rsp.statusCode = 404;
rsp.statusMessage = "Not Found";
rsp.end();
break;
}
});
console.log('MeshCommander running on HTTP port ' + settings.localport + '.');
console.log('Press ctrl-c to exit.');
}
//
// Configure Intel AMT
//
function configureAmt() {
settings.noconsole = true;
// Due to a bug in MEI handling, we have to pull MEI state first before starting LMS.
getMeiState(15, function (state) { // Flags: 1 = Versions, 2 = OsAdmin, 4 = Hashes, 8 = Network
if (state == null) { console.log("Unable to get Intel AMT state, try running as " + ((process.platform == 'win32')?"administrator.":"root.")); exit(1); return; }
2020-10-20 21:14:00 -04:00
if (state.ProvisioningState == null) { console.log('Intel AMT not ready for configuration.'); exit(1); return; }
2021-07-24 13:12:21 -04:00
getAmtOsDnsSuffix(state, function() { startLms(configureAmt2, false, state); });
});
}
2020-10-20 21:14:00 -04:00
function configureAmt2(err, state) {
console.log('Starting Intel AMT configuration...');
// Add indication if the device is battery powered, this is used to show a mobile icon when adding the device
state.isBatteryPowered = (require('identifiers').isBatteryPowered && require('identifiers').isBatteryPowered());
// Add Intel AMT credentials if provided
if ((typeof settings.password == 'string') && (settings.password != '')) {
state.amtpass = settings.password;
state.amtuser = 'admin';
if ((typeof settings.username == 'string') && (settings.username != '')) { state.amtuser = settings.username; }
}
// If a DNS suffix override is provided, use that
if (settings.dnssuffix != null) { state.DnsSuffix = settings.dnssuffix; }
// If a description is provided, send it to the server
if ((typeof settings.desc == 'string') && (settings.desc != '')) { state.desc = settings.desc; }
// Connect to MPS and start APF relay
var apfarg = {
mpsurl: settings.url,
mpsuser: settings.id.substring(0, 16),
mpspass: settings.id.substring(0, 16),
mpskeepalive: 60000,
clientname: state.OsHostname,
clientaddress: '127.0.0.1',
clientuuid: state.UUID,
conntype: 2, // 0 = CIRA, 1 = Relay, 2 = LMS. The correct value is 2 since we are performing an LMS relay.
meiState: state
};
if ((apfarg.clientuuid == null) || (apfarg.clientuuid.length != 36)) {
console.log("Unable to get Intel AMT UUID: " + apfarg.clientuuid);
exit(1); return;
} else {
settings.apftunnel = require('amt-apfclient')({ debug: (settings.debuglevel > 0) }, apfarg);
settings.apftunnel.onJsonControl = configureJsonControl;
settings.apftunnel.onChannelClosed = function () { exit(0); }
try {
settings.apftunnel.connect();
console.log("Started APF tunnel...");
} catch (e) {
console.log(JSON.stringify(e));
exit(1); return;
}
}
}
function configureJsonControl(data) {
switch (data.action) {
case 'console': // Display a console message
console.log(data.msg);
break;
case 'mestate': // Request an updated MEI state
getMeiState(15, function (state) { settings.apftunnel.updateMeiState(state); });
break;
case 'deactivate': // Request CCM deactivation
var amtMeiModule, amtMei;
try { amtMeiModule = require('amt-mei'); amtMei = new amtMeiModule(); } catch (ex) { settings.apftunnel.sendMeiDeactivationState(1); break; }
amtMei.on('error', function (e) { settings.apftunnel.sendMeiDeactivationState(1); });
amtMei.unprovision(1, function (status) { settings.apftunnel.sendMeiDeactivationState(status); }); // 0 = Success
break;
case 'startTlsHostConfig': // Request start of host based TLS ACM activation
var amtMeiModule, amtMei;
try { amtMeiModule = require('amt-mei'); amtMei = new amtMeiModule(); } catch (ex) { settings.apftunnel.sendStartTlsHostConfigResponse({ state: -103 }); break; }
amtMei.on('error', function (e) { settings.apftunnel.sendStartTlsHostConfigResponse({ state: -104 }); });
amtMei.startConfigurationHBased(Buffer.from(data.hash, 'hex'), data.hostVpn, data.dnsSuffixList, function (response) {
settings.apftunnel.sendStartTlsHostConfigResponse(response);
});
break;
2021-03-05 02:52:48 -05:00
case 'stopConfiguration': // Request Intel AMT stop configuration.
var amtMeiModule, amtMei;
try { amtMeiModule = require('amt-mei'); amtMei = new amtMeiModule(); } catch (ex) { settings.apftunnel.sendStartTlsHostConfigResponse({ state: -103 }); break; }
amtMei.on('error', function (e) { settings.apftunnel.sendStartTlsHostConfigResponse({ state: -104 }); });
amtMei.stopConfiguration(function (status) {
settings.apftunnel.sendStopConfigurationResponse(status);
});
break;
case 'close': // Close the CIRA-LMS connection
exit(0);
break;
2021-03-05 02:52:48 -05:00
default:
console.log("MeshCmd update may be needed, unknown JSON control action: " + data.action);
break;
}
}
//
// Deactivate Intel AMT CCM
//
// When called, this will use MEI to deactivate Intel AMT when it's in CCM mode. Simply calls "unprovision" on MEI and checks the return code.
function deactivateCCM() {
var amtMeiModule, amtMei;
try { amtMeiModule = require('amt-mei'); amtMei = new amtMeiModule(); } catch (ex) { console.log(ex); exit(1); return; }
2021-10-26 02:12:55 -04:00
amtMei.on('error', function (e) { console.log('deactivateCCM() error: ' + e); exit(1); return; });
amtMei.unprovision(1, function (status) { if (status == 0) { console.log('Success'); } else { console.log('Error ' + status); } exit(1); });
}
//
// Activate Intel AMT to CCM
//
function activeToCCM() {
// See if MicroLMS needs to be started and setup the $$OsAdmin wsman stack
settings.noconsole = true;
startLms(activeToCCMEx); // TODO: Fix this so that it works even if LMS already running.
}
function activeToCCMEx(state) {
if (osamtstack == null) { console.log("Unable to perform MEI operations, try running as " + ((process.platform == 'win32') ? "administrator." : "root.")); exit(1); return; }
osamtstack.BatchEnum(null, ['*AMT_GeneralSettings', '*IPS_HostBasedSetupService'], activeToCCMEx2);
}
function activeToCCMEx2(stack, name, responses, status) {
if (status != 200) { console.log('Failed to fetch activation status, status ' + status); exit(1); }
else if (responses['IPS_HostBasedSetupService'].response['AllowedControlModes'].length != 2) { console.log('Client control mode activation not allowed'); exit(1); }
else { osamtstack.IPS_HostBasedSetupService_Setup(2, md5hex('admin:' + responses['AMT_GeneralSettings'].response['DigestRealm'] + ':' + settings.password).substring(0, 32), null, null, null, null, activeToCCMEx3); }
}
function activeToCCMEx3(stack, name, responses, status) {
if (status != 200) { console.log('Failed to activate, status ' + status); }
else if (responses.Body.ReturnValue != 0) { console.log('Client control mode activation failed: ' + responses.Body.ReturnValueStr); }
else { console.log('Success'); exit(0); }
exit(1);
}
//
// Deactivate Intel AMT ACM
//
// When called, this will use MEI to deactivate Intel AMT when it's in ACM mode. Calls "unprovision" on MEI and checks the return code.
function deactivateACM() {
settings.noconsole = true;
startLms(deactivateACMEx);
}
function deactivateACMEx() {
var transport = require('amt-wsman-duk');
var wsman = require('amt-wsman');
var amt = require('amt');
wsstack = new wsman(transport, settings.hostname, settings.tls ? 16993 : 16992, settings.username, settings.password, settings.tls);
amtstack = new amt(wsstack);
amtstack.Get("AMT_SetupAndConfigurationService", function (stack, name, responses, status) {
if (status !== 200) {
console.log('Command not allowed. Status: ' + status);
exit(1);
} else {
var sacs = responses.Body;
if (sacs.ZeroTouchConfigurationEnabled == true) { sacs.ZeroTouchConfigurationEnabled = true; }
amtstack.Put("AMT_SetupAndConfigurationService", sacs, function (stack, name, responses, status) {
if (settings.type == 'full') {
amtstack.AMT_SetupAndConfigurationService_Unprovision(2, function (stack, name, responses, status) {
if (status != 200) { console.log('Failed to fully unconfigure AMT, status ' + status); exit(1); }
else if (responses.Body.ReturnValue != 0) { console.log('Unprovision failed: ' + responses.Body.ReturnValueStr); exit(1); }
else { console.log('AMT fully unprovisioned.'); exit(0); }
});
} else {
console.log('Only full unprovision is currently supported.');
exit(0);
}
//} else if (settings.type == 'partial') {
// amtstack.AMT_SetupAndConfigurationService_PartialUnprovision(null, function (stack, name, responses, status) {
// if (status != 200) { console.log('Failed to partially unconfigure AMT, status ' + status); exit(1); }
// else if (responses.Body.ReturnValue != 0) { console.log('Unprovision failed: ' + responses.Body.ReturnValueStr); exit(1); }
// else { console.log('AMT partially unprovisioned.'); exit(0); }
// });
//}
});
}
});
}
//
// Get Intel AMT activation hashes
//
var trustedHashes = null;
function getTrustedHashes(amtMei, func, tag) {
if (trustedHashes != null) { func(tag); }
trustedHashes = [];
amtMei.getHashHandles(function (handles) {
var exitOnCount = handles.length;
for (var i = 0; i < handles.length; ++i) {
this.getCertHashEntry(handles[i], function (result) {
if (result.isActive == 1) { trustedHashes.push(result.certificateHash.toLowerCase()); }
if (--exitOnCount == 0) { func(tag); }
});
}
});
}
//
// Get AMT UUID
//
// Called to get the UUID of Intel AMT, start by setting up MicroLMS if we are doing the operation on the local computer
function getAmtUuid()
{
2021-11-02 13:34:32 -04:00
if ((settings.hostname == null) || (settings.hostname == '127.0.0.1') || (settings.hostname.toLowerCase() == 'localhost'))
{
settings.hostname = '127.0.0.1';
settings.noconsole = true;
startLms(getAmtUuidEx);
return;
}
else
{
getAmtUuidEx();
}
}
// Fetch the computer's UUID by fetching the CIM_ComputerSystemPackage WSMAN object.
function getAmtUuidEx() {
var transport = require('amt-wsman-duk');
var wsman = require('amt-wsman');
var amt = require('amt');
wsstack = new wsman(transport, settings.hostname, settings.tls ? 16993 : 16992, settings.username, settings.password, settings.tls);
amtstack = new amt(wsstack);
amtstack.Get("CIM_ComputerSystemPackage", function (obj, name, response, xstatus, tag) {
if (xstatus == 200) { console.log("GUID: " + guidToStr(response.Body.PlatformGUID.toLowerCase())); } else { console.log("Intel AMT is not available or not activated."); } exit(1);
});
}
//
// FETCH ALL INTEL AMT STATE
//
function saveEntireAmtState2() {
console.log('Fetching all Intel AMT state, this may take a few minutes...');
var transport = require('amt-wsman-duk');
var wsman = require('amt-wsman');
var amt = require('amt');
wsstack = new wsman(transport, settings.hostname, settings.tls ? 16993 : 16992, settings.username, settings.password, settings.tls);
amtstack = new amt(wsstack);
amtstack.onProcessChanged = onWsmanProcessChanged;
//var AllWsman = "AMT_GeneralSystemDefenseCapabilities".split(',');
var AllWsman = "AMT_8021xCredentialContext,AMT_8021XProfile,AMT_ActiveFilterStatistics,AMT_AgentPresenceCapabilities,AMT_AgentPresenceInterfacePolicy,AMT_AgentPresenceService,AMT_AgentPresenceWatchdog,AMT_AgentPresenceWatchdogAction,AMT_AlarmClockService,IPS_AlarmClockOccurrence,AMT_AssetTable,AMT_AssetTableService,AMT_AuditLog,AMT_AuditPolicyRule,AMT_AuthorizationService,AMT_BootCapabilities,AMT_BootSettingData,AMT_ComplexFilterEntryBase,AMT_CRL,AMT_CryptographicCapabilities,AMT_EACCredentialContext,AMT_EndpointAccessControlService,AMT_EnvironmentDetectionInterfacePolicy,AMT_EnvironmentDetectionSettingData,AMT_EthernetPortSettings,AMT_EventLogEntry,AMT_EventManagerService,AMT_EventSubscriber,AMT_FilterEntryBase,AMT_FilterInSystemDefensePolicy,AMT_GeneralSettings,AMT_GeneralSystemDefenseCapabilities,AMT_Hdr8021Filter,AMT_HeuristicPacketFilterInterfacePolicy,AMT_HeuristicPacketFilterSettings,AMT_HeuristicPacketFilterStatistics,AMT_InterfacePolicy,AMT_IPHeadersFilter,AMT_KerberosSettingData,AMT_ManagementPresenceRemoteSAP,AMT_MessageLog,AMT_MPSUsernamePassword,AMT_NetworkFilter,AMT_NetworkPortDefaultSystemDefensePolicy,AMT_NetworkPortSystemDefenseCapabilities,AMT_NetworkPortSystemDefensePolicy,AMT_PCIDevice,AMT_PETCapabilities,AMT_PETFilterForTarget,AMT_PETFilterSetting,AMT_ProvisioningCertificateHash,AMT_PublicKeyCertificate,AMT_PublicKeyManagementCapabilities,AMT_PublicKeyManagementService,AMT_PublicPrivateKeyPair,AMT_RedirectionService,AMT_RemoteAccessCapabilities,AMT_RemoteAccessCredentialContext,AMT_RemoteAccessPolicyAppliesToMPS,AMT_RemoteAccessPolicyRule,AMT_RemoteAccessService,AMT_SetupAndConfigurationService,AMT_SNMPEventSubscriber,AMT_StateTransitionCondition,AMT_SystemDefensePolicy,AMT_SystemDefensePolicyInService,AMT_SystemDefenseService,AMT_SystemPowerScheme,AMT_ThirdPartyDataStorageAdministrationService,AMT_ThirdPartyDataStorageService,AMT_TimeSynchronizationService,AMT_TLSCredentialContext,AMT_TLSProtocolEndpoint,AMT_TLSProtocolEndpointCollection,AMT_TLSSettingData,AMT_TrapTargetForService,AMT_UserInitiatedConnectionService,AMT_WebUIService,AMT_WiFiPortConfigurationService,CIM_AbstractIndicationSubscription,CIM_Account,CIM_AccountManagementCapabilities,CIM_AccountManagementService,CIM_AccountOnSystem,CIM_AdminDomain,CIM_AlertIndication,CIM_AssignedIdentity,CIM_AssociatedPowerManagementService,CIM_AuthenticationService,CIM_AuthorizationService,CIM_BIOSElement,CIM_BIOSFeature,CIM_BIOSFeatureBIOSElements,CIM_BootConfigSetting,CIM_BootService,CIM_BootSettingData,CIM_BootSourceSetting,CIM_Capabilities,CIM_Card,CIM_Chassis,CIM_Chip,CIM_Collection,CIM_Component,CIM_ComputerSystem,CIM_ComputerSystemPackage,CIM_ConcreteComponent,CIM_ConcreteDependency,CIM_Controller,CIM_CoolingDevice,CIM_Credential,CIM_CredentialContext,CIM_CredentialManagementService,CIM_Dependency,CIM_DeviceSAPImplementation,CIM_ElementCapabilities,CIM_ElementConformsToProfile,CIM_ElementLocation,CIM_ElementSettingData,CIM_ElementSoftwareIdentity,CIM_ElementStatisticalData,CIM_EnabledLogicalElement,CIM_EnabledLogicalElementCapabilities,CIM_EthernetPort,CIM_Fan,CIM_FilterCollection,CIM_FilterCollectionSubscription,CIM_HostedAccessPoint,CIM_HostedDependency,CIM_HostedService,CIM_Identity,CIM_IEEE8021xCapabilities,CIM_IEEE8021xSettings,CIM_Indication,CIM_IndicationService,CIM_InstalledSoftwareIdentity,CIM_KVMRedirectionSAP,CIM_LANEndpoint,CIM_ListenerDestination,CIM_ListenerDestinationWSManagement,CIM_Location,CIM_Log,CIM_LogEntry,CIM_LogicalDevice,CIM_LogicalElement,CIM_LogicalPort,CIM_LogicalPortCapabilities,CIM_LogManagesRecord,CIM_ManagedCredential,CIM_ManagedElement,CIM_ManagedSystemElement,CIM_MediaAccessDevice,CIM_MemberOfCollection,CIM_Memory,CIM_MessageLog,CIM_NetworkPort,CIM_NetworkPortCapabilities,CIM_NetworkPortConfigurationService,CIM_OrderedComponent,CIM_OwningCollectionElement,CIM_OwningJobElement,CIM_PCIController,CIM_PhysicalComponent,CIM_PhysicalElement,CIM_PhysicalElementLocation,CIM_PhysicalFrame,CIM_PhysicalMemory,CIM_PhysicalPackage,CIM_Policy,CIM_PolicyAction,CIM_PolicyCondition,CIM_PolicyInSystem,CIM_PolicyRule,CIM_PolicyR
IntelAmtEntireStateProgress = 101;
IntelAmtEntireStateCalls = 3;
IntelAmtEntireState = { 'localtime': Date(), 'utctime': new Date().toUTCString(), 'isotime': new Date().toISOString() };
amtstack.BatchEnum(null, AllWsman, saveEntireAmtStateOk2, null, true);
amtstack.GetAuditLog(saveEntireAmtStateOk3);
amtstack.GetMessageLog(saveEntireAmtStateOk4);
}
// Save the entire Intel AMT state
function saveEntireAmtState() {
// See if MicroLMS needs to be started
if ((settings.hostname == '127.0.0.1') || (settings.hostname.toLowerCase() == 'localhost')) {
settings.noconsole = true;
startLms().then(saveEntireAmtState2);
} else {
saveEntireAmtState2();
}
}
function onWsmanProcessChanged(a, b) { var x = Math.floor((a * 100) / b); if (x < IntelAmtEntireStateProgress) { IntelAmtEntireStateProgress = x; console.log((100 - x) + '%'); } }
function saveEntireAmtStateOk2(stack, name, responses, status) { if (status == 600) { console.log('ERROR: Unable to connect to Intel(R) AMT.'); exit(2); } IntelAmtEntireState['wsmanenums'] = responses; saveEntireAmtStateDone(); }
function saveEntireAmtStateOk3(stack, messages, status) { if (status == 600) { console.log('ERROR: Unable to connect to Intel(R) AMT.'); exit(2); } IntelAmtEntireState['auditlog'] = messages; saveEntireAmtStateDone(); }
function saveEntireAmtStateOk4(stack, messages, tag, status) { if (status == 600) { console.log('ERROR: Unable to connect to Intel(R) AMT.'); exit(2); } IntelAmtEntireState['eventlog'] = messages; saveEntireAmtStateDone(); }
// Called when the entire state of Intel AMT is fetched.
function saveEntireAmtStateDone() {
if (--IntelAmtEntireStateCalls != 0) return;
var out = fs.openSync(settings.output, 'w');
fs.writeSync(out, Buffer.from(JSON.stringify(IntelAmtEntireState)));
fs.closeSync(out);
console.log('Done, results written to ' + settings.output + '.');
exit(1);
}
//
// FETCH ALL INTEL AMT MEI STATE
//
// Get Intel AMT information using MEI
// TODO: If this call is called many time at once, it's going to cause issues - Should be fixed since amtMei is now a singleton.
var getAmtInfoFetching = null;
var getAmtInfoFetchingTimer = null;
function getAmtInfo(func, tag) {
if (amtMei == null) { if (func != null) { func(null, tag); } return; }
if (getAmtInfoFetching != null) { getAmtInfoFetching.push({ f: func, t: tag }); return; }
getAmtInfoFetching = [{ f: func, t: tag }];
amtMeiTmpState = { Flags: 0, TrustedHashes: [] }; // Flags: 1=EHBC, 2=CCM, 4=ACM
getAmtInfoFetchingTimer = setTimeout(function () {
// MEI failed to respond, break out and reset everthing.
for (var i in getAmtInfoFetching) { if (getAmtInfoFetching[i].f != null) { getAmtInfoFetching[i].f(amtMeiTmpState, getAmtInfoFetching[i].t); } }
getAmtInfoFetching = null;
getAmtInfoFetchingTimer = null;
var amtMeiModule, amtMei;
try { amtMeiModule = require('amt-mei'); amtMei = new amtMeiModule(); } catch (ex) { console.log(ex); exit(1); return; }
2021-10-26 02:12:55 -04:00
amtMei.on('error', function (e) { console.log('getAmtInfo() error: ' + e); exit(1); return; });
}, 3000);
amtMei.getProtocolVersion(function (result) { if (result != null) { amtMeiTmpState.MeiVersion = result; } });
amtMei.getVersion(function (val) {
amtMeiTmpState.Versions = {};
if (val != null) {
for (var version in val.Versions) { amtMeiTmpState.Versions[val.Versions[version].Description] = val.Versions[version].Version; }
amtMei.getProvisioningMode(function (result) { if (result != null) { amtMeiTmpState.ProvisioningMode = result.mode; } });
amtMei.getProvisioningState(function (result) { if (result != null) { amtMeiTmpState.ProvisioningState = result.state; } });
amtMei.getEHBCState(function (result) { if ((result != null) && (result.EHBC == true)) { amtMeiTmpState.Flags += 1; } });
amtMei.getControlMode(function (result) { if (result != null) { if (result.controlMode == 1) { amtMeiTmpState.Flags += 2; } if (result.controlMode == 2) { amtMeiTmpState.Flags += 4; } } });
//amtMei.getMACAddresses(function (result) { if (result != null) { amtMeiTmpState.mac = result; } });
amtMei.getDnsSuffix(function (result) { if (result != null) { amtMeiTmpState.DnsSuffix = result; } });
amtMei.getHashHandles(function (handles) {
exitOnCount = handles.length;
for (var i = 0; i < handles.length; ++i) {
amtMei.getCertHashEntry(handles[i], function (result) {
amtMeiTmpState.TrustedHashes.push({ Active: result.isActive, Default: result.isDefault, HashAlgorithm: result.hashAlgorithm, Name: result.name, Hash: result.certificateHash });
if (--exitOnCount == 0) {
amtMeiTmpState.Notifications = lmsNotifications; amtMeiState = amtMeiTmpState;
for (var i in getAmtInfoFetching) { if (getAmtInfoFetching[i].f != null) { getAmtInfoFetching[i].f(amtMeiTmpState, getAmtInfoFetching[i].t); } }
getAmtInfoFetching = null;
clearTimeout(getAmtInfoFetchingTimer);
getAmtInfoFetchingTimer = null;
}
});
}
});
} else {
amtMeiState = amtMeiTmpState;
amtMeiState.ProvisioningMode = -858993460;
amtMeiState.TrustedHashes = {};
amtMeiState.Notifications = lmsNotifications;
//console.log('getAmtInfo3', JSON.stringify(amtMeiState));
if (func != null) { func(amtMeiState, tag); }
}
});
}
//
// MicroLMS
//
var lmsControlSockets = {};
var lmsControlSocketsNextId = 1;
var lmsNotifications = [];
var amtLms = null;
var promise = require('promise');
function startLms(func, lmscommander, tag) {
var ret = new promise(function (res, rej) { this._res = res; this._rej = rej; });
var lme_heci = null
try { lme_heci = require('amt-lme'); } catch (ex) { }
if (lme_heci == null) { if (func != null) { func(0, tag); } this.promise._res(); return; }
//var amtLms = null;
var http = require('http');
console.log('Setting up MEI...');
try { amtMeiModule = require('amt-mei'); amtMei = new amtMeiModule(); } catch (ex) { console.log(ex); exit(1); return; }
2021-10-26 02:12:55 -04:00
amtMei.on('error', function (e) { console.log('startLms() error: ' + e); exit(1); return; });
//console.log("PTHI Connected.");
2020-10-20 21:14:00 -04:00
try { amtLms = new lme_heci({ debug: settings.lmsdebug }); } catch (ex) { if (func != null) { func(0, tag); } return; }
amtLms.promise = ret;
amtLms.on('error', function (e) {
//console.log('LME connection failed', e);
if (lmscommander === true) { //settings.noconsole !== true) {
startMeshCommanderLms();
//console.log("LMS started, MeshCommander on HTTP/16994.");
tempTimer = setTimeout(function () { delete tempTimer; setupMeiOsAdmin(func, 2, tag); }, 100);
} else {
//console.log('LME connection failed: ' + JSON.stringify(e));
tempTimer = setTimeout(function () { delete tempTimer; setupMeiOsAdmin(func, 0, tag); }, 100);
}
this.promise._res();
});
amtLms.on('notify', function (data, options, str, code) {
if (code == 'iAMT0052-3') {
kvmGetData();
} else if (str != null) {
var notify = { date: Date.now(), str: str, code: code };
lmsNotifications.push(notify);
while (lmsNotifications.length > 100) { lmsNotifications.shift(); }
var notifyBuf = Buffer.concat([Buffer.from('0900', 'hex'), Buffer.from(JSON.stringify(notify))]) // Add a notification
for (var i in lmsControlSockets) { lmsControlSockets[i].write(notifyBuf); }
}
});
//console.log('LME Connecting...');
amtLms.on('bind', function (mapping) {
if (mapping[16992]) { this.removeAllListeners('bind'); } else { return; }
console.log('Started LMS...');
amtLms.connected = true;
this.promise._res();
//console.log("LME Connected.");
if (settings.noconsole !== true) {
startMeshCommanderLms();
//console.log("LMS started, MeshCommander on HTTP/16994.");
tempTimer = setTimeout(function () { delete tempTimer; setupMeiOsAdmin(func, 2, tag); }, 100);
//console.logReferenceCount(tempTimer);
} else {
//console.log("LMS started.");
tempTimer = setTimeout(function () { delete tempTimer; setupMeiOsAdmin(func, 1, tag); }, 100);
//console.logReferenceCount(tempTimer);
}
});
return (ret);
}
function startMeshCommanderLms() {
amtLms.meshCommander = http.createServer();
amtLms.meshCommander.listen(16994);
amtLms.meshCommander.on('upgrade', function (req, socket, head) {
//console.log("WebSocket for " + req.url.split('?')[0]);
switch (req.url.split('?')[0]) {
case '/lms.ashx': // MeshCommander control channel (PTHI)
socket.ws = socket.upgradeWebSocket();
socket.ws.on('data', processLmsControlData);
socket.ws.on('end', function () { if (lmsControlSockets[this.id]) { delete lmsControlSockets[this.id]; /*console.log('removeControl', JSON.stringify(lmsControlSockets));*/ } });
var id = lmsControlSocketsNextId++;
lmsControlSockets[id] = socket.ws;
socket.ws.id = id;
//socket.ws.write(Buffer.concat([Buffer.from('0900', 'hex'), Buffer.from(JSON.stringify(lmsNotifications))])); // Send out full list of notifications
//console.log('addControl', JSON.stringify(lmsControlSockets));
break;
case '/webrelay.ashx': // MeshCommander data channel (LME)
socket.ws = socket.upgradeWebSocket();
if (amtLms.connected == true) {
// Route traffic directly into MicroLMS
amtLms.bindDuplexStream(socket.ws, 'IPv4', 16992);
} else {
// Route traffic to real LMS service
var net = require('net');
socket.relay = net.connect({ host: '127.0.0.1', port: 16992 })
socket.relay.on('connect', function () {
socket.ws.on('data', function (data) { socket.relay.write(data); });
socket.ws.on('end', function () { socket.relay.end(); });
});
socket.relay.on('data', function (data) { socket.ws.write(data); });
socket.relay.on('close', function () { socket.ws.end(); });
}
break;
default:
socket.end();
break;
}
});
amtLms.meshCommander.on('request', function (req, rsp) {
//console.log("WebRequest for " + req.url.split('?')[0]);
switch (req.url.split('?')[0]) {
case '/': // Serve MeshCommander Web Application for LMS
var lmscommander = null;
try { lmscommander = fs.readFileSync('lmscommander.htm'); } catch (e) { }
if (lmscommander != null) {
rsp.writeHead(200, 'OK', { Server: 'JSLMS', 'Cache-Control': 'max-age=0, no-cache', 'X-Frame-Options': 'DENY', 'Content-Type': 'text/html', 'Transfer-Encoding': 'chunked' });
rsp.end(lmscommander);
} else {
rsp.writeHead(200, 'OK', { Server: 'JSLMS', 'Cache-Control': 'max-age=0, no-cache', 'X-Frame-Options': 'DENY', 'Content-Type': 'text/html', 'Content-Encoding': 'gzip', 'Transfer-Encoding': 'chunked', ETag: _IntelAmtWebApp_etag });
rsp.end(Buffer.from(_IntelAmtWebApp, "base64"));
}
break;
default: // Unknown request
rsp.statusCode = 404;
rsp.statusMessage = "Not Found";
rsp.end();
break;
}
});
}
function setupMeiOsAdmin(func, state, tag) {
if (amtMei == null) {
if (func) { func(state, tag); }
} else {
amtMei.getLocalSystemAccount(function (x) {
2020-10-20 21:14:00 -04:00
if ((x == null) || (x.user == null) || (x.pass == null)) { if (func) { func(state, tag); } return; } // No OsAdmin, stop here.
var transport = require('amt-wsman-duk');
var wsman = require('amt-wsman');
var amt = require('amt');
2021-11-02 13:34:32 -04:00
oswsstack = new wsman(transport, '127.0.0.1', 16992, x.user, x.pass, false);
osamtstack = new amt(oswsstack);
if (func) { func(state, tag); }
// Setup KVM data channel if this is Intel AMT 12 or above
amtMei.getVersion(function (x) {
var amtver = null;
try { for (var i in x.Versions) { if (x.Versions[i].Description == 'AMT') amtver = parseInt(x.Versions[i].Version.split('.')[0]); } } catch (e) { }
if ((amtver != null) && (amtver >= 12)) {
kvmGetData('skip'); // Clear any previous data, this is a dummy read to about handling old data.
tempTimer = setInterval(function () { kvmGetData(); }, 2000); // Start polling for KVM data.
kvmSetData(JSON.stringify({ action: 'restart', ver: 1 })); // Send a restart command to advise the console if present that MicroLMS just started.
}
});
});
}
}
function kvmGetData(tag) {
osamtstack.IPS_KVMRedirectionSettingData_DataChannelRead(kvmDataGetResponse, tag);
}
function kvmDataGetResponse(stack, name, response, status, tag) {
if ((tag != 'skip') && (status == 200) && (response.Body.ReturnValue == 0)) {
var val = null;
try { val = Buffer.from(response.Body.DataMessage, 'base64').toString(); } catch (e) { return }
if (val != null) { kvmProcessData(response.Body.RealmsBitmap, response.Body.MessageId, val); }
}
}
var webRtcDesktop = null;
function kvmProcessData(realms, messageId, val) {
var data = null;
try { data = JSON.parse(val) } catch (e) { }
if ((data != null) && (data.action)) {
if (data.action == 'present') { kvmSetData(JSON.stringify({ action: 'present', ver: 1, platform: process.platform })); }
if (data.action == 'offer') {
webRtcDesktop = {};
var rtc = require('ILibWebRTC');
webRtcDesktop.webrtc = rtc.createConnection();
webRtcDesktop.webrtc.on('connected', function () { });
webRtcDesktop.webrtc.on('disconnected', function () { webRtcCleanUp(); });
webRtcDesktop.webrtc.on('dataChannel', function (rtcchannel) {
webRtcDesktop.rtcchannel = rtcchannel;
var kvmmodule = require('meshDesktop');
webRtcDesktop.kvm = kvmmodule.getRemoteDesktopStream();
webRtcDesktop.kvm.pipe(webRtcDesktop.rtcchannel, { dataTypeSkip: 1, end: false });
webRtcDesktop.rtcchannel.on('end', function () { webRtcCleanUp(); });
webRtcDesktop.rtcchannel.on('data', function (x) { kvmCtrlData(this, x); });
webRtcDesktop.rtcchannel.pipe(webRtcDesktop.kvm, { dataTypeSkip: 1, end: false });
//webRtcDesktop.kvm.on('end', function () { console.log('WebRTC DataChannel closed2'); webRtcCleanUp(); });
//webRtcDesktop.rtcchannel.on('data', function (data) { console.log('WebRTC data: ' + data); });
});
kvmSetData(JSON.stringify({ action: 'answer', ver: 1, sdp: webRtcDesktop.webrtc.setOffer(data.sdp) }));
}
}
}
// Polyfill path.join
var path = {
join: function () {
var x = [];
for (var i in arguments) {
var w = arguments[i];
if (w != null) {
while (w.endsWith('/') || w.endsWith('\\')) { w = w.substring(0, w.length - 1); }
if (i != 0) {
while (w.startsWith('/') || w.startsWith('\\')) { w = w.substring(1); }
}
x.push(w);
}
}
if (x.length == 0) return '/';
return x.join('/');
}
};
// Get a formated response for a given directory path
function getDirectoryInfo(reqpath) {
var response = { path: reqpath, dir: [] };
if (((reqpath == undefined) || (reqpath == '')) && (process.platform == 'win32')) {
// List all the drives in the root, or the root itself
var results = null;
try { results = fs.readDrivesSync(); } catch (e) { } // TODO: Anyway to get drive total size and free space? Could draw a progress bar.
//console.log('a', objToString(results, 0, ' '));
if (results != null) {
for (var i = 0; i < results.length; ++i) {
var drive = { n: results[i].name, t: 1 };
if (results[i].type == 'REMOVABLE') { drive.dt = 'removable'; } // TODO: See if this is USB/CDROM or something else, we can draw icons.
response.dir.push(drive);
}
}
} else {
// List all the files and folders in this path
if (reqpath == '') { reqpath = '/'; }
var xpath = path.join(reqpath, '*');
var results = null;
try { results = fs.readdirSync(xpath); } catch (e) { }
if (results != null) {
for (var i = 0; i < results.length; ++i) {
if ((results[i] != '.') && (results[i] != '..')) {
var stat = null, p = path.join(reqpath, results[i]);
try { stat = fs.statSync(p); } catch (e) { } // TODO: Get file size/date
if ((stat != null) && (stat != undefined)) {
if (stat.isDirectory() == true) {
response.dir.push({ n: results[i], t: 2, d: stat.mtime });
} else {
response.dir.push({ n: results[i], t: 3, s: stat.size, d: stat.mtime });
}
}
}
}
}
}
return response;
}
// Process KVM control channel data
function kvmCtrlData(channel, cmd) {
if (cmd.length > 0 && cmd.charCodeAt(0) != 123) {
// This is upload data
if (this.fileupload != null) {
cmd = Buffer.from(cmd, 'base64');
var header = cmd.readUInt32BE(0);
if ((header == 0x01000000) || (header == 0x01000001)) {
fs.writeSync(this.fileupload.fp, cmd.slice(4));
channel.write({ action: 'upload', sub: 'ack', reqid: this.fileupload.reqid });
if (header == 0x01000001) { fs.closeSync(this.fileupload.fp); this.fileupload = null; } // Close the file
}
}
return;
}
//console.log('KVM Ctrl Data', cmd);
try { cmd = JSON.parse(cmd); } catch (ex) { console.error('Invalid JSON: ' + cmd); return; }
if ((cmd.path != null) && (process.platform != 'win32') && (cmd.path[0] != '/')) { cmd.path = '/' + cmd.path; } // Add '/' to paths on non-windows
switch (cmd.action) {
case 'ping': {
// This is a keep alive
channel.write({ action: 'pong' });
break;
}
case 'ls': {
/*
// Close the watcher if required
var samepath = ((this.httprequest.watcher != undefined) && (cmd.path == this.httprequest.watcher.path));
if ((this.httprequest.watcher != undefined) && (samepath == false)) {
//console.log('Closing watcher: ' + this.httprequest.watcher.path);
//this.httprequest.watcher.close(); // TODO: This line causes the agent to crash!!!!
delete this.httprequest.watcher;
}
*/
// Send the folder content to the browser
var response = getDirectoryInfo(cmd.path);
if (cmd.reqid != undefined) { response.reqid = cmd.reqid; }
channel.write(response);
/*
// Start the directory watcher
if ((cmd.path != '') && (samepath == false)) {
var watcher = fs.watch(cmd.path, onFileWatcher);
watcher.tunnel = this.httprequest;
watcher.path = cmd.path;
this.httprequest.watcher = watcher;
//console.log('Starting watcher: ' + this.httprequest.watcher.path);
}
*/
break;
}
case 'mkdir': {
// Create a new empty folder
fs.mkdirSync(cmd.path);
break;
}
case 'rm': {
// Remove many files or folders
for (var i in cmd.delfiles) {
var fullpath = path.join(cmd.path, cmd.delfiles[i]);
try { fs.unlinkSync(fullpath); } catch (e) { console.log(e); }
}
break;
}
case 'rename': {
// Rename a file or folder
var oldfullpath = path.join(cmd.path, cmd.oldname);
var newfullpath = path.join(cmd.path, cmd.newname);
try { fs.renameSync(oldfullpath, newfullpath); } catch (e) { console.log(e); }
break;
}
case 'download': {
// Download a file, to browser
var sendNextBlock = 0;
if (cmd.sub == 'start') { // Setup the download
if (this.filedownload != null) { channel.write({ action: 'download', sub: 'cancel', id: this.filedownload.id }); delete this.filedownload; }
this.filedownload = { id: cmd.id, path: cmd.path, ptr: 0 }
try { this.filedownload.f = fs.openSync(this.filedownload.path, 'rbN'); } catch (e) { channel.write({ action: 'download', sub: 'cancel', id: this.filedownload.id }); delete this.filedownload; }
if (this.filedownload) { channel.write({ action: 'download', sub: 'start', id: cmd.id }); }
} else if ((this.filedownload != null) && (cmd.id == this.filedownload.id)) { // Download commands
if (cmd.sub == 'startack') { sendNextBlock = 8; } else if (cmd.sub == 'stop') { delete this.filedownload; } else if (cmd.sub == 'ack') { sendNextBlock = 1; }
}
// Send the next download block(s)
while (sendNextBlock > 0) {
sendNextBlock--;
var buf = Buffer.alloc(4096);
var len = fs.readSync(this.filedownload.f, buf, 4, 4092, null);
this.filedownload.ptr += len;
if (len < 4092) { buf.writeInt32BE(0x01000001, 0); fs.closeSync(this.filedownload.f); delete this.filedownload; sendNextBlock = 0; } else { buf.writeInt32BE(0x01000000, 0); }
channel.write(buf.slice(0, len + 4).toString('base64')); // Write as Base64
}
break;
}
case 'upload': {
// Upload a file, from browser
if (cmd.sub == 'start') { // Start the upload
if (this.fileupload != null) { fs.closeSync(this.fileupload.fp); }
if (!cmd.path || !cmd.name) break;
this.fileupload = { reqid: cmd.reqid };
var filepath = path.join(cmd.path, cmd.name);
try { this.fileupload.fp = fs.openSync(filepath, 'wbN'); } catch (e) { }
if (this.fileupload.fp) { channel.write({ action: 'upload', sub: 'start', reqid: this.fileupload.reqid }); } else { this.fileupload = null; channel.write({ action: 'upload', sub: 'error', reqid: this.fileupload.reqid }); }
}
else if (cmd.sub == 'cancel') { // Stop the upload
if (this.fileupload != null) { fs.closeSync(this.fileupload.fp); this.fileupload = null; }
}
break;
}
case 'copy': {
// Copy a bunch of files from scpath to dspath
for (var i in cmd.names) {
var sc = path.join(cmd.scpath, cmd.names[i]), ds = path.join(cmd.dspath, cmd.names[i]);
if (sc != ds) { try { fs.copyFileSync(sc, ds); } catch (e) { } }
}
break;
}
case 'move': {
// Move a bunch of files from scpath to dspath
for (var i in cmd.names) {
var sc = path.join(cmd.scpath, cmd.names[i]), ds = path.join(cmd.dspath, cmd.names[i]);
if (sc != ds) { try { fs.copyFileSync(sc, ds); fs.unlinkSync(sc); } catch (e) { } }
}
break;
}
default:
// Unknown action, ignore it.
break;
}
}
function webRtcCleanUp() {
if (webRtcDesktop == null) return;
if (webRtcDesktop.rtcchannel) {
try { webRtcDesktop.rtcchannel.close(); } catch (e) { }
try { webRtcDesktop.rtcchannel.removeAllListeners('data'); } catch (e) { }
try { webRtcDesktop.rtcchannel.removeAllListeners('end'); } catch (e) { }
delete webRtcDesktop.rtcchannel;
}
if (webRtcDesktop.webrtc) {
try { webRtcDesktop.webrtc.close(); } catch (e) { }
try { webRtcDesktop.webrtc.removeAllListeners('connected'); } catch (e) { }
try { webRtcDesktop.webrtc.removeAllListeners('disconnected'); } catch (e) { }
try { webRtcDesktop.webrtc.removeAllListeners('dataChannel'); } catch (e) { }
delete webRtcDesktop.webrtc;
}
if (webRtcDesktop.kvm) {
try { webRtcDesktop.kvm.end(); } catch (e) { }
delete webRtcDesktop.kvm;
}
webRtcDesktop = null;
}
function kvmSetData(x) {
osamtstack.IPS_KVMRedirectionSettingData_DataChannelWrite(Buffer.from(x).toString('base64'), function () { });
}
function startLmsWsmanResponse(stack, name, responses, status) {
if (status == 600) { console.log("ERROR: Unable to connect to Intel(R) AMT."); }
else if (status != 200) { console.log("ERROR: Unable to get object from Intel(R) AMT, status = " + status + "."); }
else {
//console.log(JSON.stringify(responses), status);
var amtlogicalelements = responses['CIM_SoftwareIdentity'].responses;
if (amtlogicalelements.length > 0) {
var v = getInstance(amtlogicalelements, 'AMT')['VersionString'];
amtversion = parseInt(v.split('.')[0]);
amtversionmin = parseInt(v.split('.')[1]);
//console.log(amtversion, amtversionmin);
}
}
}
// Process commands in the LMS control channel
// Command 9 is add a notification.
function processLmsControlData(data) {
if (data.length < 2) return;
var cmdid = data.readUInt16LE(0);
switch (cmdid) {
case 1: // Request basic Intel AMT information (CMD = 1)
{ getAmtInfo(function (meinfo, socket) { meinfo.LoginMode = 2; socket.write(Buffer.concat([Buffer.from('0100', 'hex'), Buffer.from(JSON.stringify(meinfo))])); }, this); break; }
case 2: // Intel AMT MEI Unprovision (CMD = 2)
{ if (data.length < 6) break; amtMei.unprovision(data.readUInt32LE(2), function (status, socket) { var data = Buffer.alloc(6); data.writeUInt16LE(2, 0); data.writeUInt32LE(status, 2); socket.write(data); }, this); break; }
case 3: // Intel AMT MEI GetLocalSystemAccount (CMD = 3)
{ amtMei.getLocalSystemAccount(function (account, socket) { socket.write(Buffer.concat([Buffer.from('030000000000', 'hex'), account.raw])); }, this); break; }
case 4: // Instruct Intel AMT to start remote configuration (CMD = 4)
{ amtMei.startConfiguration(function (status, socket) { var data = Buffer.alloc(6); data.writeUInt16LE(7, 0); data.writeUInt32LE(status, 2); socket.write(data); }, this); break; }
case 5: // Instruct Intel AMT to stop remote configuration (CMD = 5)
{ amtMei.stopConfiguration(function (status, socket) { var data = Buffer.alloc(6); data.writeUInt16LE(7, 0); data.writeUInt32LE(status, 2); socket.write(data); }, this); break; }
case 6: // Instruct Intel AMT connect CIRA (CMD = 6)
{ amtMei.openUserInitiatedConnection(function (status, socket) { var data = Buffer.alloc(6); data.writeUInt16LE(7, 0); data.writeUInt32LE(status, 2); socket.write(data); }, this); break; }
case 7: // Instruct Intel AMT disconnect CIRA (CMD = 7)
{ amtMei.closeUserInitiatedConnection(function (status, socket) { var data = Buffer.alloc(6); data.writeUInt16LE(7, 0); data.writeUInt32LE(status, 2); socket.write(data); }, this); break; }
case 8: // Get Intel AMT CIRA State (CMD = 8)
{ amtMei.getRemoteAccessConnectionStatus(function (state, socket) { var data = Buffer.alloc(6); data.writeUInt16LE(8, 0); data.writeUInt32LE(state.status, 2); socket.write(Buffer.concat([data, state.raw])); }, this); break; }
default:
// Unknown action, ignore it.
break;
}
}
//
// MeshCentral TCP port router
//
function startRouter() {
// Start by requesting a login token, this is needed because of 2FA and check that we have correct credentials from the start
var options;
try {
2021-03-24 16:36:23 -04:00
// Parse the URL
options = http.parseUri(settings.serverurl.split('meshrelay.ashx').join('control.ashx'));
// Figure out the 2FA token to use if any
var xtoken = null;
if (settings.emailtoken) { xtoken = '**email**'; }
else if (settings.smstoken) { xtoken = '**sms**'; }
else if (settings.token != null) { xtoken = settings.token; }
// Complete the URL and add a x-meshauth header if needed
var xurlargs = [];
if (settings.serverid == null) {
// Authenticate the server using HTTPS cert hash
if (settings.authcookie != null) {
xurlargs.push('auth=' + settings.authcookie);
if (xtoken != null) { xurlargs.push('token=' + xtoken); }
2021-03-24 16:36:23 -04:00
} else {
if (xtoken != null) {
options.headers = { 'host': options.host, 'x-meshauth': Buffer.from(settings.username, 'binary').toString('base64') + ',' + Buffer.from(settings.password, 'binary').toString('base64') + ',' + Buffer.from(xtoken, 'binary').toString('base64') };
} else {
options.headers = { 'host': options.host, 'x-meshauth': Buffer.from(settings.username, 'binary').toString('base64') + ',' + Buffer.from(settings.password, 'binary').toString('base64') };
}
2021-03-24 16:36:23 -04:00
}
2021-11-03 13:58:22 -04:00
} else { options.headers = { 'host': options.host, 'x-meshauth': '*' }; } // Request inner authentication
2021-03-24 16:36:23 -04:00
if (settings.loginkey) { xurlargs.push('key=' + settings.loginkey); }
if (xurlargs.length > 0) { options.path += '?' + xurlargs.join('&'); }
} catch (e) { console.log("Unable to parse \"serverUrl\"."); exit(1); return; }
2021-03-24 16:36:23 -04:00
2021-05-25 20:10:30 -04:00
debug(1, "Connecting to " + options.host + ".");
2021-11-03 13:58:22 -04:00
debug(1, "Connection options: " + JSON.stringify(options) + ".");
options.checkServerIdentity = onVerifyServer;
options.rejectUnauthorized = false;
settings.websocket = http.request(options);
settings.websocket.upgrade = OnServerWebSocket;
settings.websocket.on('error', function (ex) { console.log("Unable to connect to server: " + JSON.stringify(ex)); exit(1); return; });
settings.websocket.on('response', function (rsp) { console.log("Unable to connect to server: " + rsp.statusMessage + " (" + rsp.statusCode + ")"); exit(1); return; });
settings.websocket.end();
}
function OnServerWebSocket(msg, s, head) {
2021-05-25 20:10:30 -04:00
debug(1, "Connected...");
settings.webchannel = s;
s.on('data', function (msg) {
var command = JSON.parse(msg);
switch (command.action) {
case 'close': {
if (command.cause == 'noauth') {
if (command.msg == 'tokenrequired') {
if (command.email2fasent === true) {
console.log("Login token email sent.");
2021-04-03 01:35:11 -04:00
} else if ((command.email2fa === true) && (command.sms2fa === true)) {
2021-03-24 16:36:23 -04:00
console.log("Login token required, use --token [token], or --emailtoken, --smstoken get a token.");
2021-04-03 01:35:11 -04:00
} else if (command.sms2fa === true) {
console.log("Login token required, use --token [token], or --smstoken get a token.");
} else if (command.email2fa === true) {
console.log("Login token required, use --token [token], or --emailtoken get a token.");
} else {
console.log("Login token required, use --token [token].");
}
2021-05-26 01:30:33 -04:00
} else if (command.msg == 'badtlscert') {
console.log("Invalid TLS certificate detected.");
} else if (command.msg == 'badargs') {
console.log("Invalid protocol arguments.");
} else {
console.log("Invalid username/password.");
}
} else { console.log("Server disconnected: " + command.msg); }
exit(1);
return;
}
case 'serverinfo': {
s.write("{\"action\":\"authcookie\"}"); // Ask for our first authentication cookie
break;
}
case 'authcookie': {
if (settings.acookie == null) {
settings.acookie = command.cookie;
settings.rcookie = command.rcookie;
settings.renewCookieTimer = setInterval(function () { settings.webchannel.write("{\"action\":\"authcookie\"}"); }, 600000); // Ask for new cookie every 10 minutes
startRouterEx();
} else {
settings.acookie = command.cookie;
settings.rcookie = command.rcookie;
}
break;
}
case 'serverAuth': {
// Check that the server certificate matches the serverid we have
var hasher = require('SHA384Stream').create();
var certDer = Buffer.from(command.cert, 'base64');
var cert = require('tls').loadCertificate({ der: certDer });
if (cert.getKeyHash().toString('hex') != settings.serverid) { console.log("Unable to authenticate the server, invalid server identifier."); exit(1); return; }
// Hash the signed data and verify the server signature
var signDataHash = hasher.syncHash(Buffer.concat([Buffer.from(settings.serverAuthClientNonce, 'base64'), Buffer.from(settings.meshServerTlsHash, 'hex'), Buffer.from(command.nonce, 'base64')]));
if (require('RSA').verify(require('RSA').TYPES.SHA384, cert, signDataHash, Buffer.from(command.signature, 'base64')) == false) { console.log("Unable to authenticate the server, invalid signature."); exit(1); return; }
2021-05-25 20:10:30 -04:00
debug(1, "Authenticated the server.");
// Switch to using HTTPS TLS certificate for authentication
delete settings.serverid;
settings.serverhttpshash = settings.meshServerTlsHash;
delete settings.meshServerTlsHash;
// Figure out the 2FA token to use if any
var xtoken = null;
if (settings.emailtoken) { xtoken = '**email**'; }
else if (settings.smstoken) { xtoken = '**sms**'; }
else if (settings.token != null) { xtoken = settings.token; }
// Authenticate the server using HTTPS cert hash
if (settings.authcookie != null) {
if (xtoken != null) {
s.write("{\"action\":\"userAuth\",\"auth\":\"" + settings.authcookie + "\",\"token\":\"" + xtoken + "\"}");
} else {
s.write("{\"action\":\"userAuth\",\"auth\":\"" + settings.authcookie + "\"}");
}
} else {
if (xtoken != null) {
s.write("{\"action\":\"userAuth\",\"username\":\"" + Buffer.from(settings.username, 'binary').toString('base64') + "\",\"password\":\"" + Buffer.from(settings.password, 'binary').toString('base64') + "\",\"token\":\"" + xtoken + "\"}");
} else {
s.write("{\"action\":\"userAuth\",\"username\":\"" + Buffer.from(settings.username, 'binary').toString('base64') + "\",\"password\":\"" + Buffer.from(settings.password, 'binary').toString('base64') + "\"}");
}
}
break;
}
}
});
s.on('error', function () { console.log("Server connection error."); exit(1); return; });
s.on('close', function () { console.log("Server closed the connection."); exit(1); return; });
// Perform inner server authentication
if (settings.serverid != null) {
2021-05-25 20:10:30 -04:00
debug(1, "Authenticating the server...");
settings.serverAuthClientNonce = require('EncryptionStream').GenerateRandom(48).toString('base64');
s.write("{\"action\":\"serverAuth\",\"cnonce\":\"" + settings.serverAuthClientNonce + "\",\"tlshash\":\"" + settings.meshServerTlsHash + "\"}"); // Ask for server authentication
}
}
function startRouterEx() {
tcpserver = net.createServer(OnTcpClientConnected);
2021-10-26 02:12:55 -04:00
tcpserver.on('error', function (e) { console.log("startRouterEx() Error: " + JSON.stringify(e)); exit(0); return; });
try {
tcpserver.listen(settings.localport, function () {
// We started listening.
if (settings.remotetarget == null) {
console.log('Redirecting local port ' + settings.localport + ' to remote port ' + settings.remoteport + '.');
} else {
console.log('Redirecting local port ' + settings.localport + ' to ' + settings.remotetarget + ':' + settings.remoteport + '.');
}
console.log("Press ctrl-c to exit.");
// If settings has a "cmd", run it now.
//process.exec("notepad.exe");
});
} catch (ex) { console.log("Unable to bind to local TCP port " + settings.localport + "."); exit(1); return; }
}
// Called when a TCP connect is received on the local port. Launch a tunnel.
function OnTcpClientConnected(c) {
try {
// 'connection' listener
debug(1, "Client connected");
c.on('end', function () { disconnectTunnel(this, this.websocket, "Client closed"); });
c.pause();
var options;
try {
options = http.parseUri(settings.serverurl + '?auth=' + settings.acookie + '&nodeid=' + settings.remotenodeid + '&tcpport=' + settings.remoteport + (settings.remotetarget == null ? '' : '&tcpaddr=' + settings.remotetarget));
} catch (e) { console.log("Unable to parse \"serverUrl\"."); exit(1); return; }
options.checkServerIdentity = onVerifyServer;
options.rejectUnauthorized = false;
c.websocket = http.request(options);
c.websocket.tcp = c;
c.websocket.tunneling = false;
c.websocket.upgrade = OnWebSocket;
2021-10-26 02:12:55 -04:00
c.websocket.on('error', function (e) { console.log("OnTcpClientConnected() Error: " + JSON.stringify(e)); });
c.websocket.end();
} catch (e) { debug(2, e); }
}
// Disconnect both TCP & WebSocket connections and display a message.
function disconnectTunnel(tcp, ws, msg) {
if (ws != null) { try { ws.end(); } catch (e) { debug(2, e); } }
if (tcp != null) { try { tcp.end(); } catch (e) { debug(2, e); } }
debug(1, "Tunnel disconnected: " + msg);
}
// Called when the web socket gets connected
function OnWebSocket(msg, s, head) {
debug(1, "Websocket connected");
s.on('data', function (msg) {
if (this.parent.tunneling == false) {
msg = msg.toString();
if ((msg == 'c') || (msg == 'cr')) {
// Pipe the connection, but don't pipe text websocket frames into the TCP socket.
this.parent.tunneling = true; this.pipe(this.parent.tcp, { dataTypeSkip: 1 }); this.parent.tcp.pipe(this); debug(1, "Tunnel active");
} else if ((msg.length > 6) && (msg.substring(0, 6) == 'error:')) {
console.log(msg.substring(6));
disconnectTunnel(this.tcp, this, msg.substring(6));
}
}
});
s.on('error', function () { disconnectTunnel(this.tcp, this, 'Websocket error'); });
s.on('close', function () { disconnectTunnel(this.tcp, this, 'Websocket closed'); });
s.parent = this;
}
// Try to discover the location of the mesh server
function discoverMeshServer() { console.log("Looking for server..."); discoveryInterval = setInterval(discoverMeshServerOnce, 5000); discoverMeshServerOnce(); }
// Try to discover the location of the mesh server only once
function discoverMeshServerOnce() {
var interfaces = os.networkInterfaces();
for (var adapter in interfaces) {
if (interfaces.hasOwnProperty(adapter)) {
for (var i = 0; i < interfaces[adapter].length; ++i) {
2021-10-26 02:12:55 -04:00
try {
var addr = interfaces[adapter][i];
if (multicastSockets[i] == null) {
multicastSockets[i] = dgram.createSocket({ type: (addr.family == 'IPv4' ? 'udp4' : 'udp6') });
multicastSockets[i].bind({ address: addr.address, exclusive: false });
}
if (addr.family == 'IPv4') {
multicastSockets[i].addMembership(membershipIPv4);
//multicastSockets[i].setMulticastLoopback(true);
multicastSockets[i].once('message', OnMulticastMessage);
multicastSockets[i].send(settings.serverid, 16989, membershipIPv4);
2021-10-26 02:12:55 -04:00
}
} catch (ex) { }
}
}
}
}
// Called when a multicast packet is received
function OnMulticastMessage(msg, rinfo) {
var m = msg.toString().split('|');
if ((m.length == 3) && (m[0] == 'MeshCentral2') && (m[1] == settings.serverid)) {
settings.serverurl = m[2].replace('%s', rinfo.address).replace('/agent.ashx', '/meshrelay.ashx');
console.log("Found server at " + settings.serverurl + ".");
if (discoveryInterval != null) { clearInterval(discoveryInterval); discoveryInterval = null; }
startRouter();
}
}
//
// IDER
//
ider = null;
iderIdleTimer = null;
// Perform IDER
function performIder() {
if ((settings.floppy != null) && fs.existsSync(settings.floppy) == false) { console.log("Unable to floppy image file: " + settings.floppy); exit(); return; }
if ((settings.cdrom != null) && fs.existsSync(settings.cdrom) == false) { console.log("Unable to CDROM image file: " + settings.cdrom); exit(); return; }
var iderStarts = ['onreboot', 'graceful', 'now'];
if ((settings.iderstart != null) && iderStarts.indexOf(settings.iderstart) < 0) { console.log("Unknown iderstart option: " + settings.iderstart); exit(); return; }
try {
var sfloppy = null, scdrom = null;
if (settings.floppy) { try { if (sfloppy = fs.statSync(settings.floppy)) { sfloppy.file = fs.openSync(settings.floppy, 'rbN'); } } catch (ex) { console.log(ex); exit(1); return; } }
if (settings.cdrom) { try { scdrom = fs.statSync(settings.cdrom); if (scdrom) { scdrom.file = fs.openSync(settings.cdrom, 'rbN'); } } catch (ex) { console.log(ex); exit(1); return; } }
ider = require('amt-redir-duk')(require('amt-ider')());
ider.onStateChanged = onIderStateChange;
ider.m.floppy = sfloppy;
ider.m.cdrom = scdrom;
if (settings.iderstart) {
ider.m.iderStart = iderStarts.indexOf(settings.iderstart);
} else {
ider.m.iderStart = 1; // OnReboot = 0, Graceful = 1, Now = 2
}
ider.m.debug = (settings.debuglevel > 0);
if (settings.timeout > 0) {
ider.m.sectorStats = iderSectorStats;
ider.m.rx_timeout = settings.timeout;
}
//ider.digestRealmMatch = wsstack.comm.digestRealm;
//ider.tlsv1only = amtstack.wsman.comm.tlsv1only;
ider.Start(settings.hostname, (settings.tls == true) ? 16995 : 16994, settings.username ? 'admin' : settings.username, settings.password, settings.tls);
} catch (ex) { console.log(ex); }
}
function onIderStateChange(stack, state) { console.log(["Disconnected", "Connecting...", "Connected...", "Started IDER..."][state]); }
function iderSectorStats(mode, dev, mediaBlocks, lba, len) {
if (iderIdleTimer != null) { clearTimeout(iderIdleTimer); }
iderIdleTimer = setTimeout(function () { console.log("Idle timeout"); exit(1); }, 1000 * settings.timeout);
}
//
// Intel AMT IPv4 wired configuration
//
function performAmtNetConfig(args) {
if ((settings.hostname == '127.0.0.1') || (settings.hostname.toLowerCase() == 'localhost')) {
settings.noconsole = true; startLms(performAmtNetConfig0, false, args);
} else {
performAmtNetConfig0(1, args);
}
}
function performAmtNetConfig0(state, args) {
var transport = require('amt-wsman-duk');
var wsman = require('amt-wsman');
var amt = require('amt');
wsstack = new wsman(transport, settings.hostname, settings.tls ? 16993 : 16992, settings.username, settings.password, settings.tls);
amtstack = new amt(wsstack);
amtstack.BatchEnum(null, ['AMT_EthernetPortSettings'], performAmtNetConfig1, args);
}
function performAmtNetConfig1(stack, name, response, status, args) {
if (status == 200) {
// Set wired and wireless interfaces
var amtwirelessif = -1;
var amtwiredif = -1;
for (var y in response['AMT_EthernetPortSettings'].responses) {
var z = response['AMT_EthernetPortSettings'].responses[y];
if (z['WLANLinkProtectionLevel'] || (y == 1)) { amtwirelessif = y; } // Set the wireless interface, this seems to cover new wireless only computers and older computers with dual interfaces.
if (y == 0) { if ((amtwirelessif != y) && (z['MACAddress'] != '00-00-00-00-00-00')) { amtwiredif = y; } } // On computers with only wireless, the wired interface will have a null MAC
}
// Check if configuration change is required
if (args) {
var docall = false;
var x = JSON.parse(JSON.stringify(response['AMT_EthernetPortSettings'].responses[amtwiredif]));
var y = response['AMT_EthernetPortSettings'].responses[amtwiredif];
delete x['IpSyncEnabled'];
delete x['LinkIsUp'];
delete x['LinkPolicy'];
delete x['MACAddress'];
delete x['SharedDynamicIP'];
delete x['SharedMAC'];
delete x['SharedStaticIp'];
if ((y['IpSyncEnabled'] == false) && (args.ipsync === '1')) { x['IpSyncEnabled'] = true; docall = true; }
if ((y['IpSyncEnabled'] == true) && (args.ipsync === '0')) { x['IpSyncEnabled'] = false; docall = true; }
if (args.dhcp && (amtwiredif != -1) && (response['AMT_EthernetPortSettings'].responses[amtwiredif].DHCPEnabled == false)) {
// Change to DHCP
x['DHCPEnabled'] = true;
docall = true;
}
else if (args.static && (amtwiredif != -1) && (response['AMT_EthernetPortSettings'].responses[amtwiredif].DHCPEnabled == true)) {
// Change to STATIC
x['DHCPEnabled'] = false;
if (args.ip) { x['IPAddress'] = args.ip; } else { console.log("Missing IPv4 address, use --ip 1.2.3.4"); exit(1); }
if (args.subnet) { x['SubnetMask'] = args.subnet; } else { console.log("Missing IPv4 subnet, use --subnet 255.255.255.0"); exit(1); }
if (args.gateway) { x['DefaultGateway'] = args.gateway; }
if (args.dns) { x['PrimaryDNS'] = args.dns; }
if (args.dns2) { x['SecondaryDNS'] = args.dns2; }
docall = true;
}
if (docall) {
if (x['DHCPEnabled'] == true) {
delete x['IPAddress'];
delete x['DefaultGateway'];
delete x['PrimaryDNS'];
delete x['SecondaryDNS'];
delete x['SubnetMask'];
}
pendingAmtConfigActions++;
//console.log(JSON.stringify(x, 4, ' '));
amtstack.Put('AMT_EthernetPortSettings', x, function (stack, name, response, status) { if (status != 200) { console.log("Error, status " + status + "."); } if (--pendingAmtConfigActions == 0) { performAmtNetConfig0(); } }, null, 0, x);
}
}
if (pendingAmtConfigActions == 0) {
var maxlen = 0;
if (amtwiredif != -1) { for (var i in response['AMT_EthernetPortSettings'].responses[amtwiredif]) { if (i.length > maxlen) { maxlen = i.length; } } }
if (amtwirelessif != -1) { for (var i in response['AMT_EthernetPortSettings'].responses[amtwirelessif]) { if (i.length > maxlen) { maxlen = i.length; } } }
if (amtwiredif != -1) { // Wired
var z = response['AMT_EthernetPortSettings'].responses[amtwiredif];
console.log("--WIRED---");
for (var i in z) {
if (['ElementName', 'InstanceID'].indexOf(i) == -1) {
var name = i;
while (name.length < maxlen) { name += ' '; }
console.log(name + ' : ' + z[i]);
}
}
}
if (amtwirelessif != -1) { // Wireless
var z = response['AMT_EthernetPortSettings'].responses[amtwirelessif];
console.log("--WIRELESS---");
for (var i in z) {
if (['ElementName', 'InstanceID'].indexOf(i) == -1) {
var name = i;
while (name.length < maxlen) { name += ' '; }
console.log(name + ' : ' + z[i]);
}
}
}
exit(0);
}
} else {
console.log("Error, status " + status + ".");
exit(1);
}
}
//
// Intel AMT Wifi configuration
//
function performAmtWifiConfig(args) {
if ((settings.hostname == '127.0.0.1') || (settings.hostname.toLowerCase() == 'localhost')) {
settings.noconsole = true; startLms(performAmtWifiConfig0, false, args);
} else {
performAmtWifiConfig0(1, args);
}
}
function performAmtWifiConfig0(state, args) {
var transport = require('amt-wsman-duk');
var wsman = require('amt-wsman');
var amt = require('amt');
wsstack = new wsman(transport, settings.hostname, settings.tls ? 16993 : 16992, settings.username, settings.password, settings.tls);
amtstack = new amt(wsstack);
amtstack.BatchEnum(null, ['CIM_WiFiEndpointSettings'], performAmtWifiConfig1, args);
}
function performAmtWifiConfig1(stack, name, response, status, args) {
if (status == 200) {
var wifiAuthMethod = { 1: "Other", 2: "Open", 3: "Shared Key", 4: "WPA PSK", 5: "WPA 802.1x", 6: "WPA2 PSK", 7: "WPA2 802.1x", 32768: "WPA3 802.1x" };
var wifiEncMethod = { 1: "Other", 2: "WEP", 3: "TKIP", 4: "CCMP", 5: "None" }
var wifiProfiles = {};
for (var y in response['CIM_WiFiEndpointSettings'].responses) {
var z = response['CIM_WiFiEndpointSettings'].responses[y];
var n = z['ElementName'];
wifiProfiles[n] = { 'Priority': z['Priority'], 'SSID': z['SSID'], 'AuthenticationMethod': z['AuthenticationMethod'], 'EncryptionMethod': z['EncryptionMethod'] };
}
if (args) {
if (args.list) {
console.log('List of Intel AMT Wifi profiles:');
if (wifiProfiles.length == 0) {
console.log('No Wifi profiles is stored.');
}
for (var t in wifiProfiles) {
var w = wifiProfiles[t];
console.log('Profile Name: ' + t + '; Priority: ' + w['Priority'] + '; SSID: ' + w['SSID'] + '; Security: ' + wifiAuthMethod[w['AuthenticationMethod']] + '/' + wifiEncMethod[w['EncryptionMethod']]);
}
exit(0);
} else if (args.add) {
if (args.auth == null) { args.auth = 6; } // if not set, default to WPA2 PSK
if (args.enc == null) { args.enc = 3; } // if not set, default to TKIP
if (args.priority == null) { args.priority = 0; } // if not set, default to 0
var wifiep = {
__parameterType: 'reference',
__resourceUri: 'http://schemas.dmtf.org/wbem/wscim/1/cim-schema/2/CIM_WiFiEndpoint',
Name: 'WiFi Endpoint 0'
};
var wifiepsettinginput = {
__parameterType: 'instance',
__namespace: 'http://schemas.dmtf.org/wbem/wscim/1/cim-schema/2/CIM_WiFiEndpointSettings',
ElementName: args.name,
InstanceID: 'Intel(r) AMT:WiFi Endpoint Settings ' + args.name,
AuthenticationMethod: args.auth,
EncryptionMethod: args.enc,
SSID: args.ssid,
Priority: args.priority,
PSKPassPhrase: args.psk
}
stack.AMT_WiFiPortConfigurationService_AddWiFiSettings(wifiep, wifiepsettinginput, null, null, null,
function (stck, nm, resp, sts) {
if (sts == 200) {
console.log("Wifi profile " + args.name + " successfully added.");
} else {
console.log("Failed to add wifi profile " + args.name + ".");
}
exit(0);
});
} else if (args.del) {
if (wifiProfiles[args.name] == null) {
console.log("Profile " + args.name + " could not be found.");
exit(0);
}
stack.Delete('CIM_WiFiEndpointSettings', { InstanceID: 'Intel(r) AMT:WiFi Endpoint Settings ' + args.name },
function (stck, nm, resp, sts) {
if (sts == 200) {
console.log("Wifi profile " + args.name + " successfully deleted.");
} else {
console.log("Failed to delete wifi profile " + args.name + ".");
}
exit(0);
},
0, 1);
}
} else {
exit(0);
}
} else {
console.log("Error, status " + status + ".");
exit(1);
}
}
//
// Intel AMT wake alarm configuration
//
function _fmtdatetime(str) {
return str.replace('T', ' ').replace('Z', '');
}
function _fmtinterval(str) {
var cl = str.replace('T', '').substring(str.indexOf('P') + 1);
cl = ' ' + cl.replace('D', " days ").replace('H', " hours ").replace('M', " minutes ");
cl = cl.replace(" 1 days ", " 1 day ").replace(" 1 hours ", " 1 hour ").replace(" 1 minutes ", " 1 minute ");
return cl.substring(0, cl.length - 1);
}
function _fmttimepad(str) {
str = '' + str;
while (str.length < 2) { str = '0' + str; }
return str;
}
function convertAmtDataStr(str) {
var timeArray = str.split('Z').join('').split('T').join('-').split(':').join('-').split('-');
return new Date(timeArray[0], timeArray[1] - 1, timeArray[2], timeArray[3], timeArray[4], timeArray[5]);
}
function prepareAlarmOccurenceTemplate(id, nm, start, interval, del) {
return '<d:AlarmTemplate xmlns:d=\"http://intel.com/wbem/wscim/1/amt-schema/1/AMT_AlarmClockService\" xmlns:s=\"http://intel.com/wbem/wscim/1/ips-schema/1/IPS_AlarmClockOccurrence\"><s:InstanceID>' + id + '</s:InstanceID><s:StartTime><p:Datetime xmlns:p=\"http://schemas.dmtf.org/wbem/wscim/1/common\">' + start + '</p:Datetime></s:StartTime><s:Interval><p:Interval xmlns:p=\"http://schemas.dmtf.org/wbem/wscim/1/common\">' + interval + '</p:Interval></s:Interval><s:DeleteOnCompletion>' + del + '</s:DeleteOnCompletion></d:AlarmTemplate>';
}
function performAmtWakeConfig(args) {
if ((settings.hostname == '127.0.0.1') || (settings.hostname.toLowerCase() == 'localhost')) {
settings.noconsole = true; startLms(performAmtWakeConfig0, false, args);
} else {
performAmtWakeConfig0(1, args);
}
}
function performAmtWakeConfig0(state, args) {
var transport = require('amt-wsman-duk');
var wsman = require('amt-wsman');
var amt = require('amt');
wsstack = new wsman(transport, settings.hostname, settings.tls ? 16993 : 16992, settings.username, settings.password, settings.tls);
amtstack = new amt(wsstack);
amtstack.BatchEnum(null, ['IPS_AlarmClockOccurrence'], performAmtWakeConfig1, args);
}
function performAmtWakeConfig1(stack, name, response, status, args) {
if (status == 200) {
var response = response['IPS_AlarmClockOccurrence'].responses;
if (!args) { exit(0); return; }
if (args.list) {
if (response.length == 0) {
console.log('No wake alarms.');
} else {
for (var i = 0; i < response.length; i++) {
var waketime = convertAmtDataStr(response[i]['StartTime']['Datetime']);
var t = waketime.toLocaleString(), tx = t.indexOf('.');
if (tx >= 0) { t = t.substring(0, tx); }
var details = response[i]['ElementName'] + ', wake on ' + t.replace(' ', ' at ');
if (response[i]['Interval'] != null) { details += ' and each' + _fmtinterval(response[i]['Interval']['Interval']); }
if (response[i]['DeleteOnCompletion'] == true) { details += ", delete when done"; }
console.log(details);
}
}
exit(0);
} else if (args.del) {
// Remove a wake alarm, start by looking to see if it exists
var alarmFound = false;
for (var i = 0; i < response.length; i++) { if (response[i]['ElementName'] == args.del) { alarmFound = true; } }
if (alarmFound == false) { console.log("Wake alarm " + args.del + " could not be found."); exit(0); return; }
// Remote the alarm
stack.Delete('IPS_AlarmClockOccurrence', { InstanceID: args.del },
function (stck, nm, resp, sts) {
if (sts == 200) { console.log("Done."); } else { console.log("Failed to delete wake alarm " + args.del + "."); }
exit(0);
},
0, 1);
} else if (args.add) {
// Add a wake alarm
var alarmFound = false;
for (var i = 0; i < response.length; i++) { if (response[i]['ElementName'] == args.add) { alarmFound = true; } }
if (alarmFound) { console.log("Wake alarm " + args.add + " already exists."); exit(0); return; }
if (typeof args.time != 'string') { args.time = '00:00:00'; }
if (typeof args.interval != 'string') { args.interval = ''; }
var alarm_name = args.add;
var x1 = args.date.split('-');
var x2 = args.time.split(':');
var t = new Date(x1[0], x1[1] - 1, x1[2], x2[0], x2[1], 0, 0); // Not sure why, but month is 0 = JAN, 11 = DEC, seconds must be 00.
var alarm_starttime = _fmttimepad(t.getFullYear()) + '-' + _fmttimepad(t.getMonth() + 1) + '-' + _fmttimepad(t.getDate()) + 'T' + _fmttimepad(t.getHours()) + ':' + _fmttimepad(t.getMinutes()) + ':' + _fmttimepad(t.getSeconds()) + 'Z';
var x = args.interval.split('-');
if (x.length != 3) { x = [0, 0, 0]; }
var alarm_interval = 'P' + x[0] + 'DT' + x[1] + 'H' + x[2] + 'M';
var alarm_doc = (args.deletewhendone != null);
var tpl = prepareAlarmOccurenceTemplate(alarm_name, alarm_name, alarm_starttime, alarm_interval, alarm_doc);
stack.wsman.ExecMethodXml(amtstack.CompleteName('AMT_AlarmClockService'), 'AddAlarm', tpl,
function (ws, resuri, response, status) {
if (status != 200) { console.log("Failed to add alarm. Status: " + status + ". Verify the alarm is for a future time."); }
else if (response.Body['ReturnValue'] != 0) { console.log("Failed to add alarm " + response.Body['ReturnValueStr'] + ". Verify the alarm is for a future time."); }
else { console.log("Done."); }
exit(0);
}
);
} else {
console.log("Unknown action, specify --list, --del or --add.");
exit(0);
}
} else {
console.log("Error, status " + status + ".");
exit(1);
}
}
//
// Intel AMT Dinamic DNS
//
function performAmtDynamicDNS(args) {
var transport = require('amt-wsman-duk');
var wsman = require('amt-wsman');
var amt = require('amt');
wsstack = new wsman(transport, settings.hostname, settings.tls ? 16993 : 16992, settings.username, settings.password, settings.tls);
amtstack = new amt(wsstack);
amtstack.BatchEnum(null, ['*AMT_GeneralSettings'], performAmtDynamicDNS1, args);
}
function performAmtDynamicDNS1(stack, name, response, status, args) {
debug(0, "performAmtDynamicDNS1(" + status + "): " + JSON.stringify(response, null, 2));
if (status == 200) {
// View the current state
var body = response['AMT_GeneralSettings'].responses.Body;
var ddnsenabled = body['DDNSUpdateEnabled'];
var ddnsserver = body['DDNSUpdateByDHCPServerEnabled'];
var ddnsinverval = body['DDNSPeriodicUpdateInterval'];
var ddnsttl = body['DDNSTTL'];
var ddnsmode = (ddnsenabled == false) ? ((ddnsserver == true) ? 'DHCP' : 'Disabled') : 'Enabled';
if (args.set || args.ttl || args.interval) {
if (args.set == 'enabled') {
body['DDNSUpdateEnabled'] = true;
body['DDNSUpdateByDHCPServerEnabled'] = false;
} else {
if (args.set == 'dhcp') {
body['DDNSUpdateEnabled'] = false;
body['DDNSUpdateByDHCPServerEnabled'] = true;
} else {
body['DDNSUpdateEnabled'] = false;
body['DDNSUpdateByDHCPServerEnabled'] = false;
}
}
if (args.interval) { body['DDNSPeriodicUpdateInterval'] = args.interval; }
if (args.ttl) { body['DDNSTTL'] = args.ttl; }
amtstack.Put('AMT_GeneralSettings', body, function (stack, name, response, status, args) {
if (status == 200) {
delete args.set;
delete args.ttl;
delete args.interval;
amtstack.BatchEnum(null, ['*AMT_GeneralSettings'], performAmtDynamicDNS1, args);
} else {
console.log('Unable to set new values, error: ' + status);
exit(1);
}
}, args);
} else {
if (ddnsmode == 'Enabled') {
console.log('Intel AMT DDNS mode: ' + ddnsmode + ', TTL: ' + ddnsttl + ' minute(s), Update Interval: ' + ddnsinverval + ' seconds(s).');
} else {
console.log('Intel AMT DDNS mode: ' + ddnsmode + '.');
}
exit(1);
}
} else { console.log("Error, status " + status + "."); exit(1); }
}
//
// Intel AMT Remote Platform Erase
//
function performAmtPlatformErase(args) {
if (!settings.tls) { console.log("Remote Platfrom Erase (RPE) is only supported over TLS, add --tls"); exit(1); return; }
var transport = require('amt-wsman-duk');
var wsman = require('amt-wsman');
var amt = require('amt');
wsstack = new wsman(transport, settings.hostname, settings.tls ? 16993 : 16992, settings.username, settings.password, settings.tls);
amtstack = new amt(wsstack);
amtstack.BatchEnum(null, ['*CIM_BootService', '*AMT_BootCapabilities'], performAmtPlatformErase1, args);
}
function performAmtPlatformErase1(stack, name, response, status, args) {
debug(0, "performAmtPlatformErase1(" + status + "): " + JSON.stringify(response, null, 2));
if (status == 200) {
// See that RPE featues are supported
var platfromEraseSupport = response['AMT_BootCapabilities'].response['PlatformErase'];
if (platfromEraseSupport == null) { console.log("Remote Platfrom Erase (RPE) is not supported on this platform"); exit(1); return; }
var supportedRpeFeatures = [];
2021-07-18 21:53:17 -04:00
if (platfromEraseSupport == 0) { supportedRpeFeatures.push("None"); } else {
if (platfromEraseSupport & (1 << 1)) { supportedRpeFeatures.push("Pyrite Revert (--pyrite)"); }
if (platfromEraseSupport & (1 << 2)) { supportedRpeFeatures.push("Secure Erase All SSDs (--ssd)"); }
if (platfromEraseSupport & (1 << 6)) { supportedRpeFeatures.push("TPM Clear (--tpm)"); }
if (platfromEraseSupport & (1 << 25)) { supportedRpeFeatures.push("Clear BIOS NVM Variables (--nvm)"); }
if (platfromEraseSupport & (1 << 26)) { supportedRpeFeatures.push("BIOS Reload of Golden Configuration (--bios)"); }
if (platfromEraseSupport & (1 << 31)) { supportedRpeFeatures.push("CSME Unconfigure (--csme)"); }
}
console.log("RPE supported features: " + supportedRpeFeatures.join(", "));
// Compute requested operations flags
var rpeflags = 0;
if (args.pyrite) { rpeflags += (1 << 1); }
if (args.ssd) { rpeflags += (1 << 2); }
if (args.tpm) { rpeflags += (1 << 6); }
if (args.nvm) { rpeflags += (1 << 25); }
if (args.bios) { rpeflags += (1 << 26); }
if (args.csme) { rpeflags += (1 << 31); }
if (rpeflags == 0) { exit(1); return; }
if ((rpeflags | platfromEraseSupport) != platfromEraseSupport) { console.log("Unable to perform unsupported RPE operation."); exit(1); return; }
settings.rpeflags = rpeflags;
settings.powerAction = 0;
if (args.reset) { settings.powerAction = 10; } else if (args.poweron) { settings.powerAction = 2; }
if (settings.powerAction == 0) { console.log("--reset or --poweron is required to perform RPE action."); exit(1); return; }
// See if OCR and RPE are enabled
var enabledState = response['CIM_BootService'].response['EnabledState'];
var enabledBootStateStr = { 0: "Unknown", 1: "Other", 2: "Enabled", 3: "Disabled", 4: "Shutting Down", 5: "Not Applicable", 6: "Enabled but Offline", 7: "In Test", 8: "Deferred", 9: "Quiesce", 10: "Starting", 32768: "OCR & RPE Disabled", 32769: "OCR Enabled, RPE Disabled", 32770: "OCR Disabled, RPE Enabled", 32771: "OCR Enabled, RPE Enabled" };
var t = enabledBootStateStr[enabledState] ? enabledBootStateStr[enabledState] : ("Unknown, #" + enabledState);
console.log("BootService enabled state: " + t);
var newEnabledState = enabledState;
if (newEnabledState < 32768) { newEnabledState = 32768; }
if ((newEnabledState & 2) == 0) {
// Enabled RPE
newEnabledState |= 2;
console.log("Enabling RPE features...");
amtstack.CIM_BootService_RequestStateChange(32771, null, performAmtPlatformErase2, args);
} else {
performAmtPlatformErase3(args);
}
} else { console.log("Error, status " + status + "."); exit(1); }
}
function performAmtPlatformErase2(stack, name, response, status, args) {
debug(0, "performAmtPlatformErase2(" + status + "): " + JSON.stringify(response, null, 2));
if (status == 200) {
if (response.Body['ReturnValueStr'] != 'SUCCESS') { console.log("Error, " + response.Body['ReturnValueStr'] + "."); exit(1); }
else { console.log("Checking enabled RPE state..."); amtstack.BatchEnum(null, ['*CIM_BootService'], performAmtPlatformErase2b, args); }
} else { console.log("Error, status " + status + "."); exit(1); }
}
function performAmtPlatformErase2b(stack, name, response, status, args) {
debug(0, "performAmtPlatformErase2b(" + status + "): " + JSON.stringify(response, null, 2));
if (status == 200) {
// See if OCR and RPE are enabled
var enabledState = response['CIM_BootService'].response['EnabledState'];
if (enabledState < 32768) { enabledState = 32768; }
if ((enabledState & 2) == 0) { console.log("RPE can't be enabled, check RPE is enabled in BIOS."); exit(1); } else { performAmtPlatformErase3(args); }
} else { console.log("Error, status " + status + "."); exit(1); }
}
function performAmtPlatformErase3(args) {
//debug(0, "performAmtPlatformErase3(" + status + "): " + JSON.stringify(response, null, 2));
var tlv = makeUefiBootParam(1, settings.rpeflags, 4), tlvlen = 1;
if ((settings.rpeflags & 2) && (typeof args.pyrite == 'string')) { tlv += makeUefiBootParam(10, args.pyrite); tlvlen++; }
if ((settings.rpeflags & 4) && (typeof args.ssd == 'string')) { tlv += makeUefiBootParam(20, args.ssd); tlvlen++; }
settings.platfromEraseTLV = { tlv: Buffer.from(tlv, 'binary').toString('base64'), tlvlen: tlvlen };
debug(0, "platfromEraseTLV: " + JSON.stringify(settings.platfromEraseTLV, null, 2));
console.log("Fetching boot information...");
amtstack.Get('AMT_BootSettingData', performAmtPlatformErase4, 0, 1);
}
function performAmtPlatformErase4(stack, name, response, status, args) {
debug(0, "performAmtPlatformErase4(" + status + "): " + JSON.stringify(response, null, 2));
if (status == 200) {
var r = response['Body'];
r['PlatformErase'] = true;
r['UefiBootParametersArray'] = settings.platfromEraseTLV.tlv;
r['UefiBootNumberOfParams'] = settings.platfromEraseTLV.tlvlen;
debug(0, "BootConfig: " + JSON.stringify(r, null, 2));
console.log("Setting boot order...");
amtstack.CIM_BootConfigSetting_ChangeBootOrder(null, function (stack, name, response, status) {
if (status != 200) { console.log("PUT CIM_BootConfigSetting_ChangeBootOrder, error #" + status + ((response.Header && response.Header.WsmanError) ? (', ' + response.Header.WsmanError) : '')); exit(1); return; }
if (response.Body['ReturnValue'] != 0) { messagebox("Error, change boot order returns " + response.Body.ReturnValueStr); exit(1); return; }
amtstack.Put('AMT_BootSettingData', r, performAmtPlatformErase5, 0, 1);
}, 0, 1);
} else { console.log("Error, status " + status + "."); exit(1); }
}
function performAmtPlatformErase5(stack, name, response, status, args) {
debug(0, "performAmtPlatformErase5(" + status + "): " + JSON.stringify(response, null, 2));
if (status == 200) {
console.log("Setting boot configuration role...");
amtstack.SetBootConfigRole(1, performAmtPlatformErase6, 0, 1);
} else { console.log("Error, status " + status + "."); exit(1); }
}
function performAmtPlatformErase6(stack, name, response, status, args) {
debug(0, "performAmtPlatformErase6(" + status + "): " + JSON.stringify(response, null, 2));
if (status == 200) {
if (response.Body['ReturnValueStr'] != 'SUCCESS') { console.log("Error, " + response.Body['ReturnValueStr'] + "."); exit(1); }
else {
console.log('Performing power state change...');
amtstack.RequestPowerStateChange(settings.powerAction, performAmtPlatformErase7); // 2 = Power Up, 10 = Reset
}
} else { console.log("Error, status " + status + "."); exit(1); }
}
function performAmtPlatformErase7(stack, name, response, status, args) {
debug(0, "performAmtPlatformErase7(" + status + "): " + JSON.stringify(response, null, 2));
if (status == 200) {
if (response.Body['ReturnValueStr'] != 'SUCCESS') { console.log("Error, " + response.Body['ReturnValueStr'] + "."); exit(1); } else { console.log('Done.'); }
exit(0);
} else { console.log("Error, status " + status + "."); exit(1); }
}
// Returns a UEFI boot parameter in binary
function makeUefiBootParam(type, data, len) {
if (typeof data == 'number') { if (len == 1) { data = String.fromCharCode(data & 0xFF); } if (len == 2) { data = ShortToStrX(data); } if (len == 4) { data = IntToStrX(data); } }
return ShortToStrX(0x8086) + ShortToStrX(type) + IntToStrX(data.length) + data;
}
function IntToStrX(v) { return String.fromCharCode(v & 0xFF, (v >> 8) & 0xFF, (v >> 16) & 0xFF, (v >> 24) & 0xFF); }
function ShortToStrX(v) { return String.fromCharCode(v & 0xFF, (v >> 8) & 0xFF); }
//
// Intel AMT feature configuration action
//
function performAmtFeatureConfig(args) {
if ((settings.hostname == '127.0.0.1') || (settings.hostname.toLowerCase() == 'localhost')) {
settings.noconsole = true; startLms(performAmtFeatureConfig0, false, args);
} else {
performAmtFeatureConfig0(1, args);
}
}
function performAmtFeatureConfig0(state, args) {
var transport = require('amt-wsman-duk');
var wsman = require('amt-wsman');
var amt = require('amt');
wsstack = new wsman(transport, settings.hostname, settings.tls ? 16993 : 16992, settings.username, settings.password, settings.tls);
amtstack = new amt(wsstack);
amtstack.BatchEnum(null, ['*IPS_OptInService', '*AMT_RedirectionService', '*CIM_KVMRedirectionSAP'], performAmtFeatureConfig1, args);
}
function performAmtFeatureConfig1(stack, name, response, status, args) {
if (status == 200) {
// User consent
var optinrequired = response['IPS_OptInService'].response['OptInRequired'];
if (args) {
if ((args.userconsent == 'none') && (optinrequired != 0)) {
pendingAmtConfigActions++;
response['IPS_OptInService'].response['OptInRequired'] = 0;
amtstack.Put('IPS_OptInService', response['IPS_OptInService'].response, function (stack, name, response, status) { if (--pendingAmtConfigActions == 0) { performAmtFeatureConfig0(); } });
}
else if ((args.userconsent == 'kvm') && (optinrequired != 1)) {
pendingAmtConfigActions++;
response['IPS_OptInService'].response['OptInRequired'] = 1;
amtstack.Put('IPS_OptInService', response['IPS_OptInService'].response, function (stack, name, response, status) { if (--pendingAmtConfigActions == 0) { performAmtFeatureConfig0(); } });
}
else if ((args.userconsent == 'all') && (optinrequired != 0xFFFFFFFF)) {
pendingAmtConfigActions++;
response['IPS_OptInService'].response['OptInRequired'] = 0xFFFFFFFF;
amtstack.Put('IPS_OptInService', response['IPS_OptInService'].response, function (stack, name, response, status) { if (--pendingAmtConfigActions == 0) { performAmtFeatureConfig0(); } });
}
}
// Redirection ports
var redirportchange = false;
var redirchange = false;
var redir = (response['AMT_RedirectionService'].response['ListenerEnabled'] == true);
var sol = ((response['AMT_RedirectionService'].response['EnabledState'] & 2) != 0);
var ider = ((response['AMT_RedirectionService'].response['EnabledState'] & 1) != 0);
if (args) {
if ((redir == false) && ((args.redir == 'enabled') || (args.redir == 1))) { response['AMT_RedirectionService'].response['ListenerEnabled'] = true; redirportchange = true; }
if ((redir == true) && ((args.redir == 'disabled') || (args.redir == 0))) { response['AMT_RedirectionService'].response['ListenerEnabled'] = false; redirportchange = true; }
if ((sol == false) && ((args.sol == 'enabled') || (args.sol == 1))) { sol = true; redirchange = true; }
if ((sol == true) && ((args.sol == 'disabled') || (args.sol == 0))) { sol = false; redirchange = true; }
if ((ider == false) && ((args.ider == 'enabled') || (args.ider == 1))) { ider = true; redirchange = true; }
if ((ider == true) && ((args.ider == 'disabled') || (args.ider == 0))) { ider = false; redirchange = true; }
if (redirportchange) { pendingAmtConfigActions++; amtstack.Put("AMT_RedirectionService", response['AMT_RedirectionService'].response, function (stack, name, response, status) { if (--pendingAmtConfigActions == 0) { performAmtFeatureConfig0(); } }); }
if (redirchange) { pendingAmtConfigActions++; amtstack.AMT_RedirectionService_RequestStateChange((32768 + ((ider ? 1 : 0) + (sol ? 2 : 0))), function (stack, name, response, status) { if (--pendingAmtConfigActions == 0) { performAmtFeatureConfig0(); } }); }
}
// KVM
var kvm = false;
var kvmchange = false;
if (response['CIM_KVMRedirectionSAP'] != null) {
kvm = ((response['CIM_KVMRedirectionSAP'].response["EnabledState"] == 6 && response['CIM_KVMRedirectionSAP'].response['RequestedState'] == 2) || response['CIM_KVMRedirectionSAP'].response['EnabledState'] == 2 || response['CIM_KVMRedirectionSAP'].response['EnabledState'] == 6);
if (args) {
if ((kvm == false) && ((args.kvm == 'enabled') || (args.kvm == 1))) { kvm = true; kvmchange = true; }
if ((kvm == true) && ((args.kvm == 'disabled') || (args.kvm == 0))) { kvm = false; kvmchange = true; }
if (kvmchange) { pendingAmtConfigActions++; amtstack.CIM_KVMRedirectionSAP_RequestStateChange(kvm ? 2 : 3, 0, function (stack, name, response, status) { if (--pendingAmtConfigActions == 0) { performAmtFeatureConfig0(); } }); }
}
}
if (pendingAmtConfigActions == 0) {
if (optinrequired == 0) { console.log("User Consent : None"); }
else if (optinrequired == 1) { console.log("User Consent : KVM"); }
else if (optinrequired == 0xFFFFFFFF) { console.log("User Consent : All"); }
else { console.log("User Consent : " + optinrequired); }
console.log("Redirection Port : " + (redir ? "Enabled" : "Disabled"));
console.log("Serial-over-LAN : " + (sol ? "Enabled" : "Disabled"));
console.log("IDE Redirection : " + (ider ? "Enabled" : 'Disabled'));
if (response['CIM_KVMRedirectionSAP'] != null) { console.log("Remote desktop (KVM) : " + (kvm ? "Enabled" : "Disabled")); }
exit(0);
}
} else {
console.log("Error, status " + status + ".");
exit(1);
}
}
//
// Intel AMT Remote Power Action
//
function performAmtPowerAction() {
var transport = require('amt-wsman-duk');
var wsman = require('amt-wsman');
var amt = require('amt');
wsstack = new wsman(transport, settings.hostname, settings.tls ? 16993 : 16992, settings.username, settings.password, settings.tls);
amtstack = new amt(wsstack);
if (settings.poweraction != 0) {
2021-03-25 16:58:24 -04:00
// Check if there is bootdevice and the command is either poweron, powercycle or reset
if ((settings.bootdevice || settings.ider_boot) && [2,5,10].indexOf(settings.poweraction)>=0) {
2021-03-25 16:58:24 -04:00
// Change boot order
amtstack.Get('AMT_BootSettingData', powerActionResponse1, 0, 1);
} else {
// Set the power state
amtstack.RequestPowerStateChange(settings.poweraction, performAmtPowerActionEx);
}
} else {
// Get the power state
amtstack.Get('CIM_AssociatedPowerManagementService', performAmtPowerActionEx2, 0, 1);
}
}
function powerActionResponse1(stack, name, response, status) {
if (status !=200) { console.log("Unable to get AMT_BootSettingData"); exit(1); return;}
var r = response.Body;
r['ConfigurationDataReset'] = false;
r['BIOSPause'] = false;
r['EnforceSecureBoot'] = false;
r['BIOSSetup'] = false;
if (settings.bootdevice && settings.bootdevice!='pxe') {
r['BootMediaIndex'] = settings.bootindex;
} else {
r['BootMediaIndex'] = 0;
}
r['FirmwareVerbosity'] = 0;
r['ForcedProgressEvents'] = false;
r['IDERBootDevice'] = settings.ider_bootindex;
r['LockKeyboard'] = false;
r['LockPowerButton'] = false;
r['LockResetButton'] = false;
r['LockSleepButton'] = false;
r['ReflashBIOS'] = false;
r['UseIDER'] = settings.ider_boot;
r['UseSOL'] = settings.ider_boot
r['UseSafeMode'] = false;
r['UserPasswordBypass'] = false;
if (r['SecureErase'] != null) {
r['SecureErase'] = false; // no secure erase
}
if (r['PlatformErase'] != null) {
r['PlatformErase'] = false; //disable platform erase
}
delete r['WinREBootEnabled'];
delete r['UEFILocalPBABootEnabled'];
delete r['UEFIHTTPSBootEnabled'];
delete r['SecureBootControlEnabled'];
delete r['BootguardStatus'];
delete r['OptionsCleared'];
delete r['BIOSLastStatus'];
delete r['UefiBootParametersArray'];
if (r['UefiBootNumberOfParams'] != null) r['UefiBootNumberOfParams'] = 0;
// Set the boot order to null, this is needed for some AMT versions that don't clear this automatically.
amtstack.CIM_BootConfigSetting_ChangeBootOrder(null, function (stack, name, response, status) {
if (status != 200) { console.log('PUT CIM_BootConfigSetting_ChangeBootOrder failed'); exit(1); return; }
if (response.Body['ReturnValue'] != 0) { console.log('(1) Change Boot Order returns '+ response.Body.ReturnValueStr); exit(1); return; }
amtstack.Put('AMT_BootSettingData', r, powerActionResponse2, 0, 1);
}, 0, 1);
}
function powerActionResponse2(stack, name, response, status, tag) {
if (status != 200) { console.log('PUT AMT_BootSettingData failed.'); exit(1); return; }
amtstack.SetBootConfigRole(1, powerActionResponse3, 0, 1);
}
function powerActionResponse3(stack, name, response, status) {
if (status != 200) { console.log('SetBootConfigRole failed.'); exit(1); return; }
var bootsources = { 'pxe' : 'Force PXE Boot', 'hdd' : 'Force Hard-drive Boot', 'cd' : 'Force CD/DVD Boot'};
var cbparam='<Address xmlns="http://schemas.xmlsoap.org/ws/2004/08/addressing">http://schemas.xmlsoap.org/ws/2004/08/addressing</Address><ReferenceParameters xmlns="http://schemas.xmlsoap.org/ws/2004/08/addressing"><ResourceURI xmlns="http://schemas.dmtf.org/wbem/wsman/1/wsman.xsd">http://schemas.dmtf.org/wbem/wscim/1/cim-schema/2/CIM_BootSourceSetting</ResourceURI><SelectorSet xmlns="http://schemas.dmtf.org/wbem/wsman/1/wsman.xsd"><Selector Name="InstanceID">Intel(r) AMT: ' + bootsources[settings.bootdevice] + '</Selector></SelectorSet></ReferenceParameters>';
if (!(settings.bootdevice in bootsources)) { cbparam=null;}
amtstack.CIM_BootConfigSetting_ChangeBootOrder(cbparam, function(st, nm, resp, sts) {
if (resp.Body['ReturnValue'] != 0) { console.log('(2) Change Boot Order returns '+ resp.Body.ReturnValueStr); exit(1); return; }
amtstack.RequestPowerStateChange(settings.poweraction, performAmtPowerActionEx);
});
}
function performAmtPowerActionEx(stack, name, response, status) {
if (status == 200) {
console.log(response.Body.ReturnValueStr.split('_').join(' '));
exit(0);
} else {
console.log("Error, status " + status + ".");
exit(1);
}
}
2020-06-15 19:37:02 -04:00
var DMTFPowerStates = ['', '', "Power on", "Light sleep", "Deep sleep", "Power cycle (Soft off)", "Off - Hard", "Hibernate (Off soft)", "Soft off", "Power cycle (Off-hard)", "Main bus reset", "Diagnostic interrupt (NMI)", "Not applicable", "Off - Soft graceful", "Off - Hard graceful", "Main bus reset graceful", "Power cycle (Off - Soft graceful)", "Power cycle (Off - Hard graceful)", "Diagnostic interrupt (INIT)"];
function performAmtPowerActionEx2(stack, name, response, status) {
if (status == 200) {
var powerNumber = parseInt(response.Body.PowerState);
if ((powerNumber >= DMTFPowerStates.length) && (powerNumber > 1)) {
console.log("Unknown power state: " + response.Body.PowerState);
} else {
console.log("Current power state: " + DMTFPowerStates[powerNumber]);
}
exit(0);
} else {
console.log("Error, status " + status + ".");
exit(1);
}
}
2020-10-20 14:28:18 -04:00
//
// Get MEI state
//
// Get Intel MEI State in a flexible way
// Flags: 1 = Versions, 2 = OsAdmin, 4 = Hashes, 8 = Network
function getMeiState(flags, func) {
var amtMeiModule, amtMei;
try { amtMeiModule = require('amt-mei'); amtMei = new amtMeiModule(); } catch (ex) { func(null); return; }
amtMei.on('error', function (e) { func(null); return; });
try {
2021-03-05 17:58:00 -05:00
var amtMeiTmpState = { 'core-ver': 1, OsHostname: require('os').hostname(), Flags: 0 }; // Flags: 1=EHBC, 2=CCM, 4=ACM
amtMei.getVersion(function (result) {
if (result == null) { func(null); return; }
amtMeiTmpState.Versions = {}; for (var version in result.Versions) { amtMeiTmpState.Versions[result.Versions[version].Description] = result.Versions[version].Version; }
amtMei.getProtocolVersion(function (result) { if (result != null) { amtMeiTmpState.MeiVersion = result; } });
//if ((flags & 1) != 0) { amtMei.getVersion(function (result) { if (result) { } }); }
amtMei.getProvisioningMode(function (result) { if (result) { amtMeiTmpState.ProvisioningMode = result.mode; } });
amtMei.getProvisioningState(function (result) { if (result) { amtMeiTmpState.ProvisioningState = result.state; } }); // 0: "Not Activated (Pre)", 1: "Not Activated (In)", 2: "Activated"
amtMei.getEHBCState(function (result) { if ((result != null) && (result.EHBC == true)) { amtMeiTmpState.Flags += 1; } });
amtMei.getControlMode(function (result) { if (result != null) { if (result.controlMode == 1) { amtMeiTmpState.Flags += 2; } if (result.controlMode == 2) { amtMeiTmpState.Flags += 4; } } }); // Flag 2 = CCM, 4 = ACM
//amtMei.getMACAddresses(function (result) { if (result) { amtMeiTmpState.mac = result; } });
if ((flags & 8) != 0) {
amtMei.getLanInterfaceSettings(0, function (result) {
if (result) {
amtMeiTmpState.net0 = result;
var fqdn = null, interfaces = require('os').networkInterfaces(); // Look for the DNS suffix for the Intel AMT Ethernet interface
for (var i in interfaces) { for (var j in interfaces[i]) { if ((interfaces[i][j].mac == amtMeiTmpState.net0.mac) && (interfaces[i][j].fqdn != null) && (interfaces[i][j].fqdn != '')) { amtMeiTmpState.OsDnsSuffix = interfaces[i][j].fqdn; } } }
}
});
amtMei.getLanInterfaceSettings(1, function (result) { if (result) { amtMeiTmpState.net1 = result; } });
}
amtMei.getUuid(function (result) { if ((result != null) && (result.uuid != null)) { amtMeiTmpState.UUID = result.uuid; } });
if ((flags & 2) != 0) { amtMei.getLocalSystemAccount(function (x) { if ((x != null) && x.user && x.pass) { amtMeiTmpState.OsAdmin = { user: x.user, pass: x.pass }; } }); }
amtMei.getDnsSuffix(function (result) { if (result != null) { amtMeiTmpState.DnsSuffix = result; } if ((flags & 4) == 0) { if (func != null) { func(amtMeiTmpState); } } });
if ((flags & 4) != 0) {
amtMei.getHashHandles(function (handles) {
if ((handles != null) && (handles.length > 0)) { amtMeiTmpState.Hashes = []; } else { func(amtMeiTmpState); }
var exitOnCount = handles.length;
for (var i = 0; i < handles.length; ++i) { this.getCertHashEntry(handles[i], function (hashresult) { amtMeiTmpState.Hashes.push(hashresult); if (--exitOnCount == 0) { if (func != null) { func(amtMeiTmpState); } } }); }
});
}
});
} catch (e) { if (func != null) { func(null); } return; }
}
2021-07-24 13:12:21 -04:00
// On non-Windows platforms, we need to query the DHCP server for the DNS suffix
function getAmtOsDnsSuffix(mestate, func) {
if ((process.platform == 'win32') || (mestate.net0 == null) || (mestate.net0.mac == null)) { func(mestate); return; }
try { require('linux-dhcp') } catch (ex) { func(mestate); return; }
require('linux-dhcp').client.info(mestate.net0.mac).then(function(d) {
if ((typeof d.options == 'object') && (typeof d.options.domainname == 'string')) { mestate.OsDnsSuffix = d.options.domainname; }
func(mestate);
}, function(e) {
console.log('DHCP error', e);
func(mestate);
});
}
//
// Startup
//
// Parse URL arguments
function parseUrlArguments(url) {
var r = {}, x = url.split('?');
if (x.length < 2) return r;
x = x[1].split('&');
for (var i in x) { var j = x[i].indexOf('='); if (j > 0) { r[x[i].substring(0, j).toLowerCase()] = x[i].substring(j + 1); } }
return r;
}
// Remove a element from a array
function removeItemFromArray(array, element) {
var index = array.indexOf(element);
if (index !== -1) { array.splice(index, 1); }
}
// Run MeshCmd, but before we do, we need to see if what type of service we are going to be
var serviceName = null, serviceDisplayName = null, serviceDesc = null;
for (var i in process.argv) {
if (process.argv[i].toLowerCase() == 'install') { process.argv[i] = '-install'; }
if (process.argv[i].toLowerCase() == 'uninstall') { process.argv[i] = '-uninstall'; }
if ((process.argv[i].toLowerCase() == 'microlms') || (process.argv[i].toLowerCase() == 'amtlms') || (process.argv[i].toLowerCase() == 'lms')) {
serviceName = 'MicroLMS';
serviceDisplayName = "MicroLMS Service for Intel(R) AMT";
serviceDesc = "Intel AMT Micro Local Manageability Service (MicroLMS)";
} else if ((process.argv[i].toLowerCase() == 'intellms')) {
serviceName = 'LMS';
serviceDisplayName = "Intel(R) Management and Security Application Local Management Service";
serviceDesc = "Intel(R) Management and Security Application Local Management Service - Provides OS-related Intel(R) ME functionality.";
} else if ((process.argv[i].toLowerCase() == 'meshcommander') || (process.argv[i].toLowerCase() == 'commander')) {
serviceName = 'MeshCommander';
serviceDisplayName = "MeshCommander, Intel AMT Management console";
serviceDesc = "MeshCommander is a Intel AMT management console.";
}
}
if (serviceName == null) {
if (process.execPath.includes('MicroLMS')) { serviceName = 'MicroLMS'; }
else if (process.execPath.includes('LMS')) { serviceName = 'LMS'; }
else if (process.execPath.includes('MeshCommander')) { serviceName = 'MeshCommander'; }
if (serviceName == null) { for (var i in process.argv) { if ((process.argv[i].toLowerCase() == '-install') || (process.argv[i].toLowerCase() == '-uninstall')) { console.log('In order to install/uninstall, a service type must be specified.'); exit(); } } }
2021-10-26 02:12:55 -04:00
if (serviceName == null) { try { run(process.argv); } catch (e) { console.log("Run() error: " + e); } }
} else {
var serviceHost = require('service-host');
var meshcmdService = new serviceHost({ name: serviceName, displayName: serviceDisplayName, startType: 'AUTO_START', description: serviceDesc });
// Called when the background service is started.
meshcmdService.on('serviceStart', function onStart() {
//process.coreDumpLocation = 'C:\\tmp\\meshcommander.dmp';
//process.on('exit', function () { console.log('exit3'); _debugCrash(); });
console.setDestination(console.Destinations.DISABLED); // Disable console.log().
//console.setDestination(console.Destinations.LOGFILE);
//attachDebuger({ webport: 0, wait: 1 }).then(console.log, console.log);
if (process.execPath.includes('MicroLMS')) { run([process.execPath, 'microlms']); } // Start MicroLMS
else if (process.execPath.includes('LMS')) { run([process.execPath, 'microlms']); } // Start MicroLMS
else if (process.execPath.includes('MeshCommander')) { run([process.execPath, 'meshcommander']); } // Start MeshCommander
else { console.log("Aborting Service Start, because unknown binary: " + process.execPath); exit(1); }
});
// Called when the background service is stopping
meshcmdService.on('serviceStop', function onStop() { console.log("Stopping service"); exit(0); }); // The console.log() is for debugging, will be ignored unless "console.setDestination()" is set.
// Called when the executable is not running as a service, run normally.
2021-10-26 02:12:55 -04:00
meshcmdService.on('normalStart', function onNormalStart() { try { run(process.argv); } catch (e) { console.log("onNormalStart() error: " + e); } });
meshcmdService.run();
}