diff --git a/agents/MeshCentralAssistant.exe b/agents/MeshCentralAssistant.exe index 9c92d8dd..de236ad6 100644 Binary files a/agents/MeshCentralAssistant.exe and b/agents/MeshCentralAssistant.exe differ diff --git a/agents/meshcore.js b/agents/meshcore.js index 8b8d59c5..88bf8795 100644 --- a/agents/meshcore.js +++ b/agents/meshcore.js @@ -218,6 +218,9 @@ function createMeshCore(agent) { case 'sessions': this._send({ cmd: 'sessions', sessions: tunnelUserCount }); break; + case 'meshToolInfo': + try { mesh.SendCommand({ action: 'meshToolInfo', name: data.name, hash: data.hash, cookie: data.cookie?true:false, pipe: true }); } catch (e) { } + break; } } catch (e) { removeRegisteredApp(this); this.end(); return; } @@ -1133,6 +1136,10 @@ function createMeshCore(agent) { r.corehashhex = getSHA384FileHash(coreDumpPath).toString('hex'); // Hash of core dump file } mesh.SendCommand(JSON.stringify(r)); + break; + case 'meshToolInfo': + if (data.pipe == true) { delete data.pipe; delete data.action; data.cmd = 'meshToolInfo'; broadcastToRegisteredApps(data); } + break; default: // Unknown action, ignore it. break; diff --git a/meshagent.js b/meshagent.js index addef162..f44906db 100644 --- a/meshagent.js +++ b/meshagent.js @@ -1397,6 +1397,16 @@ module.exports.CreateMeshAgent = function (parent, db, ws, req, args, domain) { } break; } + case 'meshToolInfo': { + if (typeof command.name != 'string') break; + var info = parent.parent.meshToolsBinaries[command.name]; + if ((command.hash != null) && (info.hash == command.hash)) return; + const responseCmd = { action: 'meshToolInfo', name: command.name, hash: info.hash, size: info.size, url: info.url }; + if (command.cookie === true) { responseCmd.url += ('&auth=' + parent.parent.encodeCookie({ download: info.dlname }, parent.parent.loginCookieEncryptionKey)); } + if (command.pipe === true) { responseCmd.pipe = true; } + try { ws.send(JSON.stringify(responseCmd)); } catch (ex) { } + break; + } default: { parent.agentStats.unknownAgentActionCount++; parent.parent.debug('agent', 'Unknown agent action (' + obj.remoteaddrport + '): ' + JSON.stringify(command) + '.'); diff --git a/meshcentral.js b/meshcentral.js index da24097c..7ee3789e 100644 --- a/meshcentral.js +++ b/meshcentral.js @@ -2106,6 +2106,7 @@ function CreateMeshCentralServer(config, args) { obj.meshToolsBinaries[this.toolname].hash = this.hash.digest('hex'); obj.meshToolsBinaries[this.toolname].hashx = this.hashx; obj.meshToolsBinaries[this.toolname].path = this.agentpath; + obj.meshToolsBinaries[this.toolname].dlname = this.dlname; obj.meshToolsBinaries[this.toolname].url = ((obj.args.notls == true) ? 'http://' : 'https://') + obj.certificates.CommonName + ':' + ((typeof obj.args.aliasport == 'number') ? obj.args.aliasport : obj.args.port) + '/meshagents?meshaction=' + this.dlname; var stats = null; try { stats = obj.fs.statSync(this.agentpath); } catch (e) { } diff --git a/views/default.handlebars b/views/default.handlebars index eb3ef8a0..f982323e 100644 --- a/views/default.handlebars +++ b/views/default.handlebars @@ -13608,7 +13608,7 @@ if (r.rights == 0xFFFFFFFF) { return 0xFFFFFFFF; } // User has full rights thru a device group link, stop here. rights = r.rights; } - + // Check permissions thru user groups var user = null; if (userid == userinfo._id) { user = userinfo; } else { if (users != null) { user = users[userid]; } } diff --git a/webserver.js b/webserver.js index 17b38d6f..8ad5186e 100644 --- a/webserver.js +++ b/webserver.js @@ -4178,8 +4178,30 @@ module.exports.CreateWebServer = function (parent, db, args, certificates) { if ((domain.loginkey != null) && (domain.loginkey.indexOf(req.query.key) == -1)) { res.sendStatus(404); return; } // Check 3FA URL key var user = obj.users[req.session.userid]; if (user == null) { + // Check if we have an authentication cookie var c = obj.parent.decodeCookie(req.query.auth, obj.parent.loginCookieEncryptionKey); - if ((c == null) || (c.userid == null)) { res.sendStatus(404); return; } + if (c == null) { res.sendStatus(404); return; } + + // Download tools using a cookie + if (c.download == req.query.meshaction) { + if (req.query.meshaction == 'winrouter') { + var p = obj.path.join(__dirname, 'agents', 'MeshCentralRouter.exe'); + if (obj.fs.existsSync(p)) { + setContentDispositionHeader(res, 'application/octet-stream', 'MeshCentralRouter.exe', null, 'MeshCentralRouter.exe'); + try { res.sendFile(p); } catch (e) { res.sendStatus(404); } + } else { res.sendStatus(404); } + } else if (req.query.meshaction == 'winassistant') { + var p = obj.path.join(__dirname, 'agents', 'MeshCentralAssistant.exe'); + if (obj.fs.existsSync(p)) { + setContentDispositionHeader(res, 'application/octet-stream', 'MeshCentralAssistant.exe', null, 'MeshCentralAssistant.exe'); + try { res.sendFile(p); } catch (e) { res.sendStatus(404); } + } else { res.sendStatus(404); } + } + return; + } + + // Check if the cookie authenticates a user + if (c.userid == null) { res.sendStatus(404); return; } user = obj.users[c.userid]; if (user == null) { res.sendStatus(404); return; } }