Skip to content

Commit

Permalink
Release 2.4.0
Browse files Browse the repository at this point in the history
  • Loading branch information
wh1te909 committed Sep 24, 2022
2 parents caa5cd8 + 43d13a7 commit d7560b0
Show file tree
Hide file tree
Showing 12 changed files with 192 additions and 80 deletions.
25 changes: 18 additions & 7 deletions agent/agent.go
Original file line number Diff line number Diff line change
Expand Up @@ -76,6 +76,12 @@ const (
winExeName = "tacticalrmm.exe"
winSvcName = "tacticalrmm"
meshSvcName = "mesh agent"
etcConfig = "/etc/tacticalagent"
nixAgentDir = "/opt/tacticalagent"
nixAgentBin = nixAgentDir + "/tacticalagent"
macPlistPath = "/Library/LaunchDaemons/tacticalagent.plist"
macPlistName = "tacticalagent"
macMeshSvcDir = "/usr/local/mesh_services"
)

var winTempDir = filepath.Join(os.Getenv("PROGRAMDATA"), "TacticalRMM")
Expand Down Expand Up @@ -120,13 +126,18 @@ func New(logger *logrus.Logger, version string) *Agent {
}

var MeshSysExe string
if len(ac.CustomMeshDir) > 0 {
MeshSysExe = filepath.Join(ac.CustomMeshDir, "MeshAgent.exe")
} else {
MeshSysExe = filepath.Join(os.Getenv("ProgramFiles"), "Mesh Agent", "MeshAgent.exe")
}

if runtime.GOOS == "linux" {
switch runtime.GOOS {
case "windows":
if len(ac.CustomMeshDir) > 0 {
MeshSysExe = filepath.Join(ac.CustomMeshDir, "MeshAgent.exe")
} else {
MeshSysExe = filepath.Join(os.Getenv("ProgramFiles"), "Mesh Agent", "MeshAgent.exe")
}
case "linux":
MeshSysExe = "/opt/tacticalmesh/meshagent"
case "darwin":
MeshSysExe = "/usr/local/mesh_services/meshagent/meshagent"
default:
MeshSysExe = "/opt/tacticalmesh/meshagent"
}

Expand Down
39 changes: 32 additions & 7 deletions agent/agent_unix.go
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,7 @@ func (a *Agent) GetDisks() []trmm.Disk {
}

for _, p := range partitions {
if strings.Contains(p.Device, "dev/loop") {
if strings.Contains(p.Device, "dev/loop") || strings.Contains(p.Device, "devfs") {
continue
}
usage, err := disk.Usage(p.Mountpoint)
Expand Down Expand Up @@ -283,7 +283,7 @@ func (a *Agent) AgentUpdate(url, inno, version string) {
}
}

if a.seEnforcing() {
if runtime.GOOS == "linux" && a.seEnforcing() {
se := a.NewCMDOpts()
se.Command = fmt.Sprintf("restorecon -rv %s", self)
out := a.CmdV2(se)
Expand All @@ -292,7 +292,15 @@ func (a *Agent) AgentUpdate(url, inno, version string) {

opts := a.NewCMDOpts()
opts.Detached = true
opts.Command = "systemctl restart tacticalagent.service"
switch runtime.GOOS {
case "linux":
opts.Command = "systemctl restart tacticalagent.service"
case "darwin":
opts.Command = "launchctl kickstart -k system/tacticalagent"
default:
return
}

a.CmdV2(opts)
}

Expand All @@ -310,7 +318,9 @@ func (a *Agent) AgentUninstall(code string) {
opts := a.NewCMDOpts()
opts.IsScript = true
opts.Shell = f.Name()
opts.Args = []string{"uninstall"}
if runtime.GOOS == "linux" {
opts.Args = []string{"uninstall"}
}
opts.Detached = true
a.CmdV2(opts)
}
Expand Down Expand Up @@ -354,7 +364,15 @@ func (a *Agent) getMeshNodeID() (string, error) {
func (a *Agent) RecoverMesh() {
a.Logger.Infoln("Attempting mesh recovery")
opts := a.NewCMDOpts()
opts.Command = "systemctl restart meshagent.service"
def := "systemctl restart meshagent.service"
switch runtime.GOOS {
case "linux":
opts.Command = def
case "darwin":
opts.Command = "launchctl kickstart -k system/meshagent"
default:
opts.Command = def
}
a.CmdV2(opts)
a.SyncMeshNodeID()
}
Expand Down Expand Up @@ -413,18 +431,25 @@ func (a *Agent) GetWMIInfo() map[string]interface{} {
wmiInfo["make_model"] = ""
chassis, err := ghw.Chassis(ghw.WithDisableWarnings())
if err != nil {
a.Logger.Errorln("ghw.Chassis()", err)
a.Logger.Debugln("ghw.Chassis()", err)
} else {
if chassis.Vendor != "" || chassis.Version != "" {
wmiInfo["make_model"] = fmt.Sprintf("%s %s", chassis.Vendor, chassis.Version)
}
}

if runtime.GOOS == "darwin" {
opts := a.NewCMDOpts()
opts.Command = "sysctl hw.model"
out := a.CmdV2(opts)
wmiInfo["make_model"] = strings.ReplaceAll(out.Stdout, "hw.model: ", "")
}

// gfx cards

gpu, err := ghw.GPU(ghw.WithDisableWarnings())
if err != nil {
a.Logger.Errorln("ghw.GPU()", err)
a.Logger.Debugln("ghw.GPU()", err)
} else {
for _, i := range gpu.GraphicsCards {
if i.DeviceInfo != nil {
Expand Down
12 changes: 0 additions & 12 deletions agent/agent_windows.go
Original file line number Diff line number Diff line change
Expand Up @@ -653,18 +653,6 @@ func (a *Agent) AgentUninstall(code string) {
cmd.Start()
}

func (a *Agent) addDefenderExlusions() {
code := fmt.Sprintf(`
Add-MpPreference -ExclusionPath '%s\*'
Add-MpPreference -ExclusionPath '%s\*'
Add-MpPreference -ExclusionPath '%s\*'
`, winTempDir, a.ProgramDir, winMeshDir)
_, _, _, err := a.RunScript(code, "powershell", []string{}, 20, false)
if err != nil {
a.Logger.Debugln(err)
}
}

// RunMigrations cleans up unused stuff from older agents
func (a *Agent) RunMigrations() {
for _, i := range []string{"nssm.exe", "nssm-x86.exe"} {
Expand Down
95 changes: 78 additions & 17 deletions agent/install.go
Original file line number Diff line number Diff line change
Expand Up @@ -140,34 +140,57 @@ func (a *Agent) Install(i *Installer) {
installerMeshSystemEXE = a.MeshSystemEXE
}

var meshNodeID string
var meshNodeID, meshOutput string

if !i.NoMesh && runtime.GOOS != "linux" {
switch runtime.GOOS {
case "windows":
meshOutput = filepath.Join(a.ProgramDir, a.MeshInstaller)
case "darwin":
tmp, err := createTmpFile()
if err != nil {
a.Logger.Fatalln("Failed to create mesh temp file", err)
}
meshOutput = tmp.Name()
os.Chmod(meshOutput, 0755)
defer os.Remove(meshOutput)
defer os.Remove(meshOutput + ".msh")
}

if runtime.GOOS == "windows" && !i.NoMesh {
mesh := filepath.Join(a.ProgramDir, a.MeshInstaller)
if i.LocalMesh == "" {
if runtime.GOOS == "windows" && i.LocalMesh != "" {
err := copyFile(i.LocalMesh, meshOutput)
if err != nil {
a.installerMsg(err.Error(), "error", i.Silent)
}
} else {
a.Logger.Infoln("Downloading mesh agent...")
payload := map[string]string{"goarch": a.GoArch, "plat": a.Platform}
r, err := rClient.R().SetBody(payload).SetOutput(mesh).Post(fmt.Sprintf("%s/api/v3/meshexe/", baseURL))
r, err := rClient.R().SetBody(payload).SetOutput(meshOutput).Post(fmt.Sprintf("%s/api/v3/meshexe/", baseURL))
if err != nil {
a.installerMsg(fmt.Sprintf("Failed to download mesh agent: %s", err.Error()), "error", i.Silent)
}
if r.StatusCode() != 200 {
a.installerMsg(fmt.Sprintf("Unable to download the mesh agent from the RMM. %s", r.String()), "error", i.Silent)
}
} else {
err := copyFile(i.LocalMesh, mesh)
if err != nil {
a.installerMsg(err.Error(), "error", i.Silent)
}
}

a.Logger.Infoln("Installing mesh agent...")
a.Logger.Debugln("Mesh agent:", mesh)
a.Logger.Debugln("Mesh agent:", meshOutput)
time.Sleep(1 * time.Second)

meshNodeID, err = a.installMesh(mesh, installerMeshSystemEXE, i.Proxy)
if err != nil {
a.installerMsg(fmt.Sprintf("Failed to install mesh agent: %s", err.Error()), "error", i.Silent)
if runtime.GOOS == "windows" {
meshNodeID, err = a.installMesh(meshOutput, installerMeshSystemEXE, i.Proxy)
if err != nil {
a.installerMsg(fmt.Sprintf("Failed to install mesh agent: %s", err.Error()), "error", i.Silent)
}
} else {
opts := a.NewCMDOpts()
opts.Command = fmt.Sprintf("%s -install", meshOutput)
out := a.CmdV2(opts)
if out.Status.Exit != 0 {
a.Logger.Fatalln("Error installing mesh agent:", out.Stderr)
}
fmt.Println(out.Stdout)
}
}

Expand Down Expand Up @@ -219,6 +242,47 @@ func (a *Agent) Install(i *Installer) {
// check in once
a.DoNatsCheckIn()

if runtime.GOOS == "darwin" {
os.MkdirAll(nixAgentDir, 0755)
self, _ := os.Executable()
copyFile(self, nixAgentBin)
os.Chmod(nixAgentBin, 0755)
svc := fmt.Sprintf(`
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>Label</key>
<string>%s</string>
<key>ServiceDescription</key>
<string>TacticalAgent Service</string>
<key>ProgramArguments</key>
<array>
<string>%s</string>
<string>-m</string>
<string>svc</string>
</array>
<key>WorkingDirectory</key>
<string>%s/</string>
<key>RunAtLoad</key>
<true/>
<key>KeepAlive</key>
<true/>
</dict>
</plist>
`, macPlistName, nixAgentBin, nixAgentDir)

os.WriteFile(macPlistPath, []byte(svc), 0644)
opts := a.NewCMDOpts()
opts.Command = fmt.Sprintf("launchctl bootstrap system %s", macPlistPath)
a.CmdV2(opts)
}

if runtime.GOOS == "windows" {
// send software api
a.SendSoftware()
Expand All @@ -245,9 +309,6 @@ func (a *Agent) Install(i *Installer) {
a.installerMsg(out.ErrorMsg, "error", i.Silent)
}

a.Logger.Infoln("Adding windows defender exclusions")
a.addDefenderExlusions()

if i.Power {
a.Logger.Infoln("Disabling sleep/hibernate...")
DisableSleepHibernate()
Expand Down
36 changes: 29 additions & 7 deletions agent/install_unix.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,17 +15,16 @@ https://license.tacticalrmm.com
package agent

import (
"fmt"
"log"
"os"
"runtime"
"time"

"github.com/spf13/viper"
trmm "github.com/wh1te909/trmm-shared"
)

const (
etcConfig = "/etc/tacticalagent"
)

func (a *Agent) checkExistingAndRemove(silent bool) {}

func (a *Agent) installerMsg(msg, alert string, silent bool) {
if alert == "error" {
a.Logger.Fatalln(msg)
Expand All @@ -51,7 +50,30 @@ func createAgentConfig(baseurl, agentid, apiurl, token, agentpk, cert, proxy, me
}
}

func (a *Agent) addDefenderExlusions() {}
func (a *Agent) checkExistingAndRemove(silent bool) {
if runtime.GOOS == "darwin" {
if trmm.FileExists(a.MeshSystemEXE) {
a.Logger.Infoln("Existing meshagent found, attempting to remove...")
uopts := a.NewCMDOpts()
uopts.Command = fmt.Sprintf("%s -fulluninstall", a.MeshSystemEXE)
uout := a.CmdV2(uopts)
fmt.Println(uout.Stdout)
time.Sleep(1 * time.Second)
}

if trmm.FileExists(macPlistPath) {
a.Logger.Infoln("Existing tacticalagent plist found, attempting to remove...")
opts := a.NewCMDOpts()
opts.Command = fmt.Sprintf("launchctl bootout system %s", macPlistPath)
a.CmdV2(opts)
}

os.RemoveAll(macMeshSvcDir)
os.Remove(etcConfig)
os.RemoveAll(nixAgentDir)
os.Remove(macPlistPath)
}
}

func DisableSleepHibernate() {}

Expand Down
17 changes: 11 additions & 6 deletions agent/svc.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ https://license.tacticalrmm.com
package agent

import (
"runtime"
"sync"
"time"

Expand All @@ -27,11 +28,13 @@ func (a *Agent) RunAsService() {
}

func (a *Agent) AgentSvc() {
go a.GetPython(false)
if runtime.GOOS == "windows" {
go a.GetPython(false)

err := createWinTempDir()
if err != nil {
a.Logger.Errorln("AgentSvc() createWinTempDir():", err)
err := createWinTempDir()
if err != nil {
a.Logger.Errorln("AgentSvc() createWinTempDir():", err)
}
}
a.RunMigrations()

Expand All @@ -53,8 +56,10 @@ func (a *Agent) AgentSvc() {
go a.SyncMeshNodeID()

time.Sleep(time.Duration(randRange(1, 3)) * time.Second)
a.AgentStartup()
a.SendSoftware()
if runtime.GOOS == "windows" {
a.AgentStartup()
a.SendSoftware()
}

checkInHelloTicker := time.NewTicker(time.Duration(randRange(30, 60)) * time.Second)
checkInAgentInfoTicker := time.NewTicker(time.Duration(randRange(200, 400)) * time.Second)
Expand Down
2 changes: 1 addition & 1 deletion build/rmm.exe.manifest
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
<assemblyIdentity
type="win32"
name="TacticalRMM"
version="2.3.1.0"
version="2.4.0.0"
processorArchitecture="*"/>
<trustInfo xmlns="urn:schemas-microsoft-com:asm.v3">
<security>
Expand Down
2 changes: 1 addition & 1 deletion build/setup.iss
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
#define MyAppName "Tactical RMM Agent"
#define MyAppVersion "2.3.1"
#define MyAppVersion "2.4.0"
#define MyAppPublisher "AmidaWare LLC"
#define MyAppURL "https://github.com/amidaware"
#define MyAppExeName "tacticalrmm.exe"
Expand Down
Loading

0 comments on commit d7560b0

Please sign in to comment.