Added server support for agent update using meshcore.
Ylian Saint-Hilaire committed
Jan 14, 2021 at 16:17 UTC
2f5482e230b1c558b7da12767b8761841576fc7d
2 files changed
+36
-11
agents/recoverycore.js
+1
-1
@@ -88,7 +88,7 @@ function getServerTargetUrlEx(url) {
88
89
require('MeshAgent').on('Connected', function () {
90
require('os').name().then(function (v) {
91
- sendConsoleText("Mesh Agent Receovery Console, OS: " + v);
91
+ //sendConsoleText("Mesh Agent Receovery Console, OS: " + v);
92
require('MeshAgent').SendCommand(meshCoreObj);
93
});
94
});
meshagent.js
+35
-10
@@ -167,7 +167,7 @@ module.exports.CreateMeshAgent = function (parent, db, ws, req, args, domain) {
167
// If we have a core, use it.
168
if (corename != null) {
169
const meshcorehash = parent.parent.defaultMeshCoresHash[corename];
170
- if (agentMeshCoreHash != meshcorehash) {
170
+ if ((agentMeshCoreHash != meshcorehash) || (obj.agentCoreUpdate === true)) {
171
if ((obj.agentCoreCheck < 5) || (obj.agentCoreCheck == 1001)) {
172
if (meshcorehash == null) {
173
// Clear the core
@@ -187,7 +187,7 @@ module.exports.CreateMeshAgent = function (parent, db, ws, req, args, domain) {
187
obj.agentCoreUpdatePending = true;
188
parent.parent.taskLimiter.launch(function (argument, taskid, taskLimiterQueue) {
189
if (obj.authenticated == 2) {
190
- // Send the updated code.
190
+ // Send the updated core.
191
delete obj.agentCoreUpdatePending;
192
obj.sendBinary(common.ShortToStr(10) + common.ShortToStr(0) + argument.hash + argument.core, function () { parent.parent.taskLimiter.completed(taskid); }); // MeshCommand_CoreModule, start core update
193
parent.agentStats.updatingCoreCount++;
@@ -234,7 +234,15 @@ module.exports.CreateMeshAgent = function (parent, db, ws, req, args, domain) {
234
else if (cmdid == 12) { // MeshCommand_AgentHash
235
if ((msg.length == 52) && (obj.agentExeInfo != null) && (obj.agentExeInfo.update == true)) {
236
const agenthash = msg.substring(4);
237
- if (compareAgentBinaryHash(obj.agentExeInfo, agenthash)) {
237
+ const agentUpdateMethod = compareAgentBinaryHash(obj.agentExeInfo, agenthash)
238
+ if (agentUpdateMethod === 2) { // Use meshcore agent update system
239
+ // Send the recovery core to the agent, if the agent is capable of running one
240
+ if (((obj.agentInfo.capabilities & 16) != 0) && (parent.parent.meshAgentsArchitectureNumbers[obj.agentInfo.agentId].core != null)) {
241
+ obj.agentCoreCheck = 1001;
242
+ obj.agentCoreUpdate = true;
243
+ obj.sendBinary(common.ShortToStr(11) + common.ShortToStr(0)); // Command 11, ask for mesh core hash.
244
+ }
245
+ } else if (agentUpdateMethod === 1) { // Use native agent update system
246
// Mesh agent update required, do it using task limiter so not to flood the network. Medium priority task.
247
parent.parent.taskLimiter.launch(function (argument, taskid, taskLimiterQueue) {
248
if (obj.authenticated != 2) { parent.parent.taskLimiter.completed(taskid); return; } // If agent disconnection, complete and exit now.
@@ -518,7 +526,7 @@ module.exports.CreateMeshAgent = function (parent, db, ws, req, args, domain) {
526
if ((msg.substring(2, 34) == parent.swarmCertificateHash256) || (msg.substring(2, 50) == parent.swarmCertificateHash384)) { obj.useSwarmCert = true; }
527
} else if (cmd == 30) {
528
// Agent Commit Date. This is future proofing. Can be used to change server behavior depending on the date range of the agent.
521
- //console.log('Connected Agent Commit Date: ' + msg.substring(2));
529
+ //console.log('Connected Agent Commit Date: ' + msg.substring(2) + ", " + Date.parse(msg.substring(2)));
530
}
531
}
532
});
@@ -1140,8 +1148,21 @@ module.exports.CreateMeshAgent = function (parent, db, ws, req, args, domain) {
1148
}
1149
case 'coreinfo':
1150
{
1143
- // Sent by the agent to update agent information
1144
- ChangeAgentCoreInfo(command);
1151
+ if ((obj.agentCoreUpdate === true) && (obj.agentExeInfo != null)) {
1152
+ // Agent update. The recovery core was loaded in the agent, send a command to update the agent
1153
+ var cmd = { action: 'agentUpdate', url: obj.agentExeInfo.url, hash: obj.agentExeInfo.hashhex };
1154
+ // Add server TLS cert hash
1155
+ if (parent.parent.args.ignoreagenthashcheck !== true) {
1156
+ const tlsCertHash = parent.webCertificateFullHashs[domain.id];
1157
+ if (tlsCertHash != null) { cmd.servertlshash = Buffer.from(tlsCertHash, 'binary').toString('hex'); }
1158
+ }
1159
+ // Send the agent update command
1160
+ obj.send(JSON.stringify(cmd));
1161
+ delete obj.agentCoreUpdate;
1162
+ } else {
1163
+ // Sent by the agent to update agent information
1164
+ ChangeAgentCoreInfo(command);
1165
+ }
1166
break;
1167
}
1168
case 'smbios':
@@ -1669,15 +1690,19 @@ module.exports.CreateMeshAgent = function (parent, db, ws, req, args, domain) {
1690
}
1691
1692
// Check if we need to update this agent, return true if agent binary update required.
1693
+ // Return 0 is no update needed, 1 update using native system, 2 update using meshcore system
1694
function compareAgentBinaryHash(agentExeInfo, agentHash) {
1695
// If we are testing the agent update system, always return true
1674
- if (args.agentupdatetest === true) return true;
1696
+ if ((args.agentupdatetest === true) || (args.agentupdatetest === 1)) return 1;
1697
+ if (args.agentupdatetest === 2) return 2;
1698
// If the hash matches or is null, no update required.
1676
- if ((agentExeInfo.hash == agentHash) || (agentHash == '\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0')) return false;
1699
+ if ((agentExeInfo.hash == agentHash) || (agentHash == '\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0')) return 0;
1700
// If this is a macOS x86 or ARM agent type and it matched the universal binary, no update required.
1678
- if (((agentExeInfo.id == 16) || (agentExeInfo.id == 29)) && (parent.parent.meshAgentBinaries[10005].hash == agentHash)) return false;
1701
+ if (((agentExeInfo.id == 16) || (agentExeInfo.id == 29)) && (parent.parent.meshAgentBinaries[10005].hash == agentHash)) return 0;
1702
+
1703
// No match, update the agent.
1680
- return true;
1704
+ if ((agentExeInfo.id == 3) && (agentExeInfo.id == 4)) return 2; // For Windows agents, use the meshcore update technique.
1705
+ return 1; // For all other agents, use the native update technique.
1706
}
1707
1708
// Request that the core dump file on this agent be uploaded to the server