Nightshift v3 — Security Foot-Gun Analysis
Repo: Microck/tailstick
Language: Go
Task: security-footgun
Date: 2026-04-17
Executive Summary
Analyzed 23 Go source files in the tailstick codebase — a Tailscale VPN GUI/CLI management tool. 10 security findings identified across P1–P3 severity. No P0 (Critical) findings.
Good practices observed: AES-GCM with scrypt, constant-time password comparison, file-based auth key passing, input validation.
Findings Summary
| # |
Severity |
File |
Category |
| 1 |
P1 |
internal/gui/server.go |
Unauthenticated HTTP GUI server |
| 2 |
P1 |
internal/config/config.go |
os.ExpandEnv enables env var injection |
| 3 |
P1 |
internal/crypto/secret.go |
Machine-mode encryption key weakly bound |
| 4 |
P2 |
internal/gui/server.go |
Config errors leak internal details via HTTP |
| 5 |
P2 |
internal/gui/server.go |
Enrollment error details exposed in HTTP |
| 6 |
P2 |
internal/tailscale/client.go |
API response body in error messages |
| 7 |
P2 |
internal/tailscale/client.go |
Auth key temp file briefly world-readable |
| 8 |
P2 |
internal/state/store.go |
State directories created with 0o755 |
| 9 |
P3 |
internal/tailscale/client.go |
`curl |
| 10 |
P3 |
internal/gui/server.go |
Operator password over plaintext HTTP |
P1: Unauthenticated GUI Server (server.go:65-106)
HTTP server exposes /api/enroll without auth. Any local user process can trigger enrollment. Host can be set to 0.0.0.0 via CLI flag — still no auth.
Fix: Add session/token auth middleware. Bind to loopback only. Reject 0.0.0.0 binding.
P1: os.ExpandEnv Injection (config.go:31)
Config file passed through os.ExpandEnv before JSON parsing — ${VAR} patterns expanded. An attacker controlling any part of the config can read any environment variable.
Fix: Restrict expansion to known safe variables only. Remove blanket os.ExpandEnv.
P1: Weak Machine-Mode Key (secret.go:114-127)
Machine-mode encryption key derived only from GOOS|GOARCH|hostname|machine-id — deterministic and guessable.
Fix: Include high-entropy secret stored separately.
P2: Error Info Leakage (server.go:113-117, 173-174)
Config load errors and enrollment errors returned verbatim in HTTP responses. May leak file paths, config structure, API details.
Fix: Log full errors server-side; return generic messages to clients.
P2: Auth Key TOCTOU (client.go:172-196)
Auth key written to temp file before chmod(0o600) — brief world-readable window.
Fix: Use os.OpenFile with 0o600 directly.
P2: World-Readable Directories (store.go:41,67)
State/audit parent directories created with 0o755 instead of 0o700.
Fix: Use 0o700 for directories containing sensitive data.
Automated by Nightshift v3 (GLM 5.1)
Nightshift v3 — Security Foot-Gun Analysis
Repo: Microck/tailstick
Language: Go
Task: security-footgun
Date: 2026-04-17
Executive Summary
Analyzed 23 Go source files in the tailstick codebase — a Tailscale VPN GUI/CLI management tool. 10 security findings identified across P1–P3 severity. No P0 (Critical) findings.
Good practices observed: AES-GCM with scrypt, constant-time password comparison, file-based auth key passing, input validation.
Findings Summary
internal/gui/server.gointernal/config/config.goos.ExpandEnvenables env var injectioninternal/crypto/secret.gointernal/gui/server.gointernal/gui/server.gointernal/tailscale/client.gointernal/tailscale/client.gointernal/state/store.gointernal/tailscale/client.gointernal/gui/server.goP1: Unauthenticated GUI Server (
server.go:65-106)HTTP server exposes
/api/enrollwithout auth. Any local user process can trigger enrollment. Host can be set to0.0.0.0via CLI flag — still no auth.Fix: Add session/token auth middleware. Bind to loopback only. Reject
0.0.0.0binding.P1:
os.ExpandEnvInjection (config.go:31)Config file passed through
os.ExpandEnvbefore JSON parsing —${VAR}patterns expanded. An attacker controlling any part of the config can read any environment variable.Fix: Restrict expansion to known safe variables only. Remove blanket
os.ExpandEnv.P1: Weak Machine-Mode Key (
secret.go:114-127)Machine-mode encryption key derived only from
GOOS|GOARCH|hostname|machine-id— deterministic and guessable.Fix: Include high-entropy secret stored separately.
P2: Error Info Leakage (
server.go:113-117, 173-174)Config load errors and enrollment errors returned verbatim in HTTP responses. May leak file paths, config structure, API details.
Fix: Log full errors server-side; return generic messages to clients.
P2: Auth Key TOCTOU (
client.go:172-196)Auth key written to temp file before
chmod(0o600)— brief world-readable window.Fix: Use
os.OpenFilewith0o600directly.P2: World-Readable Directories (
store.go:41,67)State/audit parent directories created with
0o755instead of0o700.Fix: Use
0o700for directories containing sensitive data.Automated by Nightshift v3 (GLM 5.1)