diff --git a/agents/meshcore.js b/agents/meshcore.js index 12b958c7..ee3d56ee 100644 --- a/agents/meshcore.js +++ b/agents/meshcore.js @@ -622,7 +622,7 @@ if ((require('fs').existsSync(process.cwd() + 'batterystate.txt')) && (require(' else { try { // Setup normal battery monitoring - if (require('identifiers').isBatteryPowered && require('identifiers').isBatteryPowered()) { + if (require('computer-identifiers').isBatteryPowered && require('computer-identifiers').isBatteryPowered()) { require('MeshAgent')._battLevelChanged = function _battLevelChanged(val) { _battLevelChanged.self._currentBatteryLevel = val; _battLevelChanged.self.SendCommand({ action: 'battery', state: _battLevelChanged.self._currentPowerState, level: val }); @@ -657,14 +657,14 @@ try { require('os').name().then(function (v) { meshCoreObj.osdesc = v; meshCoreO // Get Volumes and BitLocker if Windows try { if (process.platform == 'win32'){ - if (require('identifiers').volumes_promise != null){ - var p = require('identifiers').volumes_promise(); + if (require('computer-identifiers').volumes_promise != null){ + var p = require('computer-identifiers').volumes_promise(); p.then(function (res){ meshCoreObj.volumes = res; meshCoreObjChanged(); }); - }else if (require('identifiers').volumes != null){ - meshCoreObj.volumes = require('identifiers').volumes(); + }else if (require('computer-identifiers').volumes != null){ + meshCoreObj.volumes = require('computer-identifiers').volumes(); meshCoreObjChanged(); } } @@ -1813,7 +1813,7 @@ function onFileWatcher(a, b) { */ // Replace all key name spaces with _ in an object recursively. -// This is a workaround since require('identifiers').get() returns key names with spaces in them on Linux. +// This is a workaround since require('computer-identifiers').get() returns key names with spaces in them on Linux. function replaceSpacesWithUnderscoresRec(o) { if (typeof o != 'object') return; for (var i in o) { if (i.indexOf(' ') >= 0) { o[i.split(' ').join('_')] = o[i]; delete o[i]; } replaceSpacesWithUnderscoresRec(o[i]); } @@ -1821,8 +1821,7 @@ function replaceSpacesWithUnderscoresRec(o) { function getSystemInformation(func) { try { - var results = { hardware: require('identifiers').get() }; // Hardware info - + var results = { hardware: require('computer-identifiers').get() }; // Hardware info if (results.hardware && results.hardware.windows) { // Remove extra entries and things that change quickly var x = results.hardware.windows.osinfo; @@ -1873,9 +1872,11 @@ function getSystemInformation(func) { } if(results.hardware && results.hardware.linux) { if (!results.hardware.identifiers['bios_serial']) { - if (require('fs').statSync('/sys/class/dmi/id/product_serial').isFile()){ - results.hardware.identifiers['bios_serial'] = require('fs').readFileSync('/sys/class/dmi/id/product_serial').toString().trim(); - } + try { + if (require('fs').statSync('/sys/class/dmi/id/product_serial').isFile()){ + results.hardware.identifiers['bios_serial'] = require('fs').readFileSync('/sys/class/dmi/id/product_serial').toString().trim(); + } + } catch (ex) { } } if (!results.hardware.identifiers['bios_mode']) { try { @@ -1928,9 +1929,9 @@ function getSystemInformation(func) { { results.pendingReboot = require('win-info').pendingReboot(); // Pending reboot - if (require('identifiers').volumes_promise != null) + if (require('computer-identifiers').volumes_promise != null) { - var p = require('identifiers').volumes_promise(); + var p = require('computer-identifiers').volumes_promise(); p.then(function (res) { results.hardware.windows.volumes = res; @@ -1938,9 +1939,9 @@ function getSystemInformation(func) { func(results); }); } - else if (require('identifiers').volumes != null) + else if (require('computer-identifiers').volumes != null) { - results.hardware.windows.volumes = require('identifiers').volumes(); + results.hardware.windows.volumes = require('computer-identifiers').volumes(); results.hash = hasher.syncHash(JSON.stringify(results)).toString('hex'); func(results); } @@ -4250,7 +4251,7 @@ function processConsoleCommand(cmd, args, rights, sessionid) { } break; case 'vm': - response = 'Virtual Machine = ' + require('identifiers').isVM(); + response = 'Virtual Machine = ' + require('computer-identifiers').isVM(); break; case 'startupoptions': response = JSON.stringify(require('MeshAgent').getStartupOptions()); diff --git a/agents/modules_meshcore/computer-identifiers.js b/agents/modules_meshcore/computer-identifiers.js new file mode 100644 index 00000000..ff3123f7 --- /dev/null +++ b/agents/modules_meshcore/computer-identifiers.js @@ -0,0 +1,775 @@ +/* +Copyright 2019-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. +*/ + +function trimIdentifiers(val) +{ + for(var v in val) + { + if (!val[v] || val[v] == 'None' || val[v] == '') { delete val[v]; } + } +} +function trimResults(val) +{ + var i, x; + for (i = 0; i < val.length; ++i) + { + for (x in val[i]) + { + if (x.startsWith('_')) + { + delete val[i][x]; + } + else + { + if (val[i][x] == null || val[i][x] == 0) + { + delete val[i][x]; + } + } + } + } +} +function brief(headers, obj) +{ + var i, x; + for (x = 0; x < obj.length; ++x) + { + for (i in obj[x]) + { + if (!headers.includes(i)) + { + delete obj[x][i]; + } + } + } + return (obj); +} + +function dataHandler(c) +{ + this.str += c.toString(); +} + +function linux_identifiers() +{ + var identifiers = {}; + var ret = {}; + var values = {}; + + if (!require('fs').existsSync('/sys/class/dmi/id')) { + if(require('fs').existsSync('/sys/firmware/devicetree/base/model')){ + if(require('fs').readFileSync('/sys/firmware/devicetree/base/model').toString().trim().startsWith('Raspberry')){ + identifiers['board_vendor'] = 'Raspberry Pi'; + identifiers['board_name'] = require('fs').readFileSync('/sys/firmware/devicetree/base/model').toString().trim(); + identifiers['board_serial'] = require('fs').readFileSync('/sys/firmware/devicetree/base/serial-number').toString().trim(); + }else{ + throw('Unknown board'); + } + }else { + throw ('this platform does not have DMI statistics'); + } + } else { + var entries = require('fs').readdirSync('/sys/class/dmi/id'); + for(var i in entries) + { + if (require('fs').statSync('/sys/class/dmi/id/' + entries[i]).isFile()) + { + try + { + ret[entries[i]] = require('fs').readFileSync('/sys/class/dmi/id/' + entries[i]).toString().trim(); + } + catch(z) + { + } + if (ret[entries[i]] == 'None') { delete ret[entries[i]];} + } + } + entries = null; + + identifiers['bios_date'] = ret['bios_date']; + identifiers['bios_vendor'] = ret['bios_vendor']; + identifiers['bios_version'] = ret['bios_version']; + identifiers['bios_serial'] = ret['product_serial']; + identifiers['board_name'] = ret['board_name']; + identifiers['board_serial'] = ret['board_serial']; + identifiers['board_vendor'] = ret['board_vendor']; + identifiers['board_version'] = ret['board_version']; + identifiers['product_uuid'] = ret['product_uuid']; + identifiers['product_name'] = ret['product_name']; + } + + try { + identifiers['bios_mode'] = (require('fs').statSync('/sys/firmware/efi').isDirectory() ? 'UEFI': 'Legacy'); + } catch (ex) { identifiers['bios_mode'] = 'Legacy'; } + + var child = require('child_process').execFile('/bin/sh', ['sh']); + child.stdout.str = ''; child.stdout.on('data', dataHandler); + child.stdin.write('cat /proc/cpuinfo | grep "model name" | ' + "tr '\\n' ':' | awk -F: '{ print $2 }'\nexit\n"); + child.waitExit(); + identifiers['cpu_name'] = child.stdout.str.trim(); + child = null; + + + // Fetch GPU info + child = require('child_process').execFile('/bin/sh', ['sh']); + child.stdout.str = ''; child.stdout.on('data', dataHandler); + child.stdin.write("lspci | grep ' VGA ' | tr '\\n' '`' | awk '{ a=split($0,lines" + ',"`"); printf "["; for(i=1;i1)'); + child.stdin.write(' {'); + child.stdin.write(' sub(/^[ \\t]*/,"",tmp[2]);'); + child.stdin.write(' gsub(/ /,"",tmp[1]);'); + child.stdin.write(' printf("%s\\"%s\\": \\"%s\\"", ccx, tmp[1], tmp[2]);'); + child.stdin.write(' ccx=",";'); + child.stdin.write(' }'); + child.stdin.write(' }'); + child.stdin.write(' printf("}}");'); + child.stdin.write(' comma=",";'); + child.stdin.write(' }'); + child.stdin.write(' }'); + child.stdin.write(' printf("]");'); + child.stdin.write("}'\nexit\n"); + child.waitExit(); + + try + { + var j = JSON.parse(child.stdout.str); + var i, key, key2; + for (i = 0; i < j.length; ++i) + { + for (key in j[i]) + { + delete j[i][key]['ArrayHandle']; + delete j[i][key]['ErrorInformationHandle']; + for (key2 in j[i][key]) + { + if (j[i][key][key2] == 'Unknown' || j[i][key][key2] == 'Not Specified' || j[i][key][key2] == '') + { + delete j[i][key][key2]; + } + } + } + } + + if(j.length > 0){ + var mem = {}; + for (i = 0; i < j.length; ++i) + { + for (key in j[i]) + { + if (mem[key] == null) { mem[key] = []; } + mem[key].push(j[i][key]); + } + } + values.linux.memory = mem; + } + } + catch (e) + { } + child = null; + } + + var usbdevices = require('lib-finder').findBinary('usb-devices'); + if (usbdevices != null) + { + var child = require('child_process').execFile('/bin/sh', ['sh']); + child.stdout.str = ''; child.stdout.on('data', dataHandler); + child.stderr.str = ''; child.stderr.on('data', dataHandler); + child.stdin.write(usbdevices + " | tr '\\n' '`' | "); + child.stdin.write(" awk '"); + child.stdin.write('{'); + child.stdin.write(' comma="";'); + child.stdin.write(' printf("[");'); + child.stdin.write(' len=split($0, group, "``");'); + child.stdin.write(' for(i=1;i<=len;++i)'); + child.stdin.write(' {'); + child.stdin.write(' comma2="";'); + child.stdin.write(' xlen=split(group[i], line, "`");'); + child.stdin.write(' scount=0;'); + child.stdin.write(' for(x=1;x0)'); + child.stdin.write(' {'); + child.stdin.write(' printf("%s{", comma); comma=",";'); + child.stdin.write(' for(x=1;x2) { print \"true\"; }}'\nexit\n"); + child.waitExit(); + if(child.stdout.str.trim() != '') { ret = true; } + break; + } + return (ret); +}; +module.exports.isVM = function isVM() +{ + var ret = false; + var id = this.get(); + if (id.linux && id.linux.sys_vendor) + { + switch (id.linux.sys_vendor) + { + case 'VMware, Inc.': + case 'QEMU': + case 'Xen': + ret = true; + break; + default: + break; + } + } + if (id.identifiers.bios_vendor) + { + switch(id.identifiers.bios_vendor) + { + case 'VMware, Inc.': + case 'Xen': + case 'SeaBIOS': + ret = true; + break; + default: + break; + } + } + if (id.identifiers.board_vendor && id.identifiers.board_vendor == 'VMware, Inc.') { ret = true; } + if (id.identifiers.board_name) + { + switch (id.identifiers.board_name) + { + case 'VirtualBox': + case 'Virtual Machine': + ret = true; + break; + default: + break; + } + } + + if (process.platform == 'win32' && !ret) + { + for(var i in id.identifiers.gpu_name) + { + if(id.identifiers.gpu_name[i].startsWith('VMware ')) + { + ret = true; + break; + } + } + } + + + if (!ret) { ret = this.isDocker(); } + return (ret); +}; + +if (process.platform == 'win32') +{ + module.exports.volumes_promise = windows_volumes; +} + +// bios_date = BIOS->ReleaseDate +// bios_vendor = BIOS->Manufacturer +// bios_version = BIOS->SMBIOSBIOSVersion +// board_name = BASEBOARD->Product = ioreg/board-id +// board_serial = BASEBOARD->SerialNumber = ioreg/serial-number | ioreg/IOPlatformSerialNumber +// board_vendor = BASEBOARD->Manufacturer = ioreg/manufacturer +// board_version = BASEBOARD->Version \ No newline at end of file