package miragebrand

import (
	"os"
	"path/filepath"
	"strings"

	"tailscale.com/version"
)

const (
	productName        = "Mirage"
	serviceName        = "miraged"
	stateFileName      = "server-state.conf"
	registryBase       = `SOFTWARE\Mirage IPN`
	policyRegistryBase = `SOFTWARE\Policies\Mirage`
	guiExecutableName  = "MirageGUI.exe"
	cliExecutableName  = "mirage.exe"
	legacyGUIExeName   = "Mirage.exe"
	linuxSocketPath    = "/run/mirage/miraged.sock"
	linuxStateFile     = "/var/lib/mirage/miraged.state"
	linuxTunName       = "mirage0"
)

func ProductName() string {
	return productName
}

func ServiceName() string {
	return serviceName
}

func WindowsPipePath() string {
	return `\\.\pipe\ProtectedPrefix\Administrators\Mirage\miraged`
}

func WindowsStateFile(programData string) string {
	return filepath.Join(programData, productName, stateFileName)
}

func WindowsLegacyStateFile(localAppData string) string {
	return filepath.Join(localAppData, productName, stateFileName)
}

func RegistryBase() string {
	return registryBase
}

func PolicyRegistryBase() string {
	return policyRegistryBase
}

func WindowsKnownProcessNames() []string {
	return []string{"mirage", "miraged"}
}

func WindowsGUIExecutableName() string {
	return guiExecutableName
}

func WindowsCLIExecutableName() string {
	return cliExecutableName
}

func WindowsLegacyGUIExecutableNames() []string {
	return []string{guiExecutableName, legacyGUIExeName}
}

func normalizeBinaryName(name string) string {
	name = strings.ToLower(filepath.Base(strings.TrimSpace(name)))
	name = strings.TrimSuffix(name, ".exe")
	return name
}

func IsMirageBinaryName(name string) bool {
	switch normalizeBinaryName(name) {
	case "mirage", "mirage-cli", "miraged", "mirage-qt", "mirage-qt-ui":
		return true
	default:
		return false
	}
}

func CurrentProcessUsesMirageBranding() bool {
	if IsMirageBinaryName(version.CmdName()) {
		return true
	}
	if len(os.Args) > 0 && IsMirageBinaryName(os.Args[0]) {
		return true
	}
	return false
}

func LinuxSocketPath() string {
	return linuxSocketPath
}

func LinuxStateFile() string {
	return linuxStateFile
}

func LinuxServiceUnit() string {
	return serviceName + ".service"
}

func LinuxTunName() string {
	return linuxTunName
}

func WindowsTunName() string {
	return productName
}

func LinuxStateFileBaseName() string {
	return "miraged.state"
}

func DaemonBinaryName() string {
	return serviceName
}

func CanonicalCLIName(binaryName string) string {
	if IsMirageBinaryName(binaryName) {
		return "mirage"
	}
	return "tailscale"
}
