mirror of
https://github.com/gesellix/Bose-SoundTouch.git
synced 2026-08-19 00:56:16 +00:00
docs(zeroconf): clearer literal-IP error and a Security Considerations note
Building on the strict literal-IP validator from the previous commit, make the runtime error self-explanatory so anyone tripping on a hostname URL can fix it in one shot: * Errors now lead with the offending zeroconf URL and the rejected host, so wrapping by GetInfo / PushCredentials / pushSimplifiedToken doesn't bury the actual bad value. * The "host must be a literal IP" error suggests two concrete one-liner resolutions (`getent hosts <name>` and `dig +short <name>`) so the user has a copy-paste fix. * The "host is not on a local network" error names the accepted ranges (loopback / RFC1918 private / link-local v4+v6) so the user knows what they're allowed to pass. docs/guides/SOUNDTOUCH-SERVICE.md gains a bullet under Security Considerations explaining the constraint and the rationale (LAN-resident SSRF surface), so the strict behaviour is documented rather than a surprise. The 17 TestValidateZcBaseURL cases still pass — only the message bodies changed. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 4.7
parent
fbde4e136f
commit
dc1f811a81
@@ -836,6 +836,7 @@ fi
|
||||
- **SSH Access**: Migration requires SSH access to devices. Ensure your network security policies allow this.
|
||||
- **Proxy Logging**: Disable `REDACT_PROXY_LOGS` only in development environments.
|
||||
- **Data Protection**: The data directory contains device configurations and usage patterns. Secure appropriately.
|
||||
- **Spotify / Amazon Music credential push (zeroconf)**: outbound credential-push requests are restricted to literal IP hosts on local-network ranges (loopback, RFC1918 private, IPv4/IPv6 link-local). Hostname-style URLs (DNS, mDNS `*.local`) are rejected at runtime; if you have a hostname, resolve it first (`getent hosts <name>` or `dig +short <name>`) and pass the resolved IP. This guards against a malicious LAN-resident speaker pointing the credential push at a non-speaker host (server-side request forgery).
|
||||
|
||||
## Performance Tuning
|
||||
|
||||
|
||||
@@ -192,25 +192,32 @@ func DecryptBlob(encKey, macKey, blob []byte) ([]byte, error) {
|
||||
func validateZcBaseURL(zcBaseURL string) (*url.URL, error) {
|
||||
u, err := url.Parse(zcBaseURL)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("parse: %w", err)
|
||||
return nil, fmt.Errorf("zeroconf URL %q: parse: %w", zcBaseURL, err)
|
||||
}
|
||||
|
||||
if u.Scheme != "http" && u.Scheme != "https" {
|
||||
return nil, fmt.Errorf("scheme %q not allowed (expected http or https)", u.Scheme)
|
||||
return nil, fmt.Errorf("zeroconf URL %q: scheme %q not allowed — must be http or https", zcBaseURL, u.Scheme)
|
||||
}
|
||||
|
||||
host := u.Hostname()
|
||||
if host == "" {
|
||||
return nil, fmt.Errorf("missing host")
|
||||
return nil, fmt.Errorf("zeroconf URL %q: missing host", zcBaseURL)
|
||||
}
|
||||
|
||||
ip := net.ParseIP(host)
|
||||
if ip == nil {
|
||||
return nil, fmt.Errorf("host %q must be a literal IP (DNS/mDNS hostnames are not supported on this path; resolve to a private IP before calling)", host)
|
||||
return nil, fmt.Errorf(
|
||||
"zeroconf URL %q: host %q must be a literal IP — resolve the hostname to a private-network IP first "+
|
||||
"(e.g. `getent hosts %s` or `dig +short %s`) and retry with the resolved address",
|
||||
zcBaseURL, host, host, host)
|
||||
}
|
||||
|
||||
if !ip.IsLoopback() && !ip.IsPrivate() && !ip.IsLinkLocalUnicast() {
|
||||
return nil, fmt.Errorf("host %q is not on a local network", host)
|
||||
return nil, fmt.Errorf(
|
||||
"zeroconf URL %q: host %q is not on a local network — only loopback (127.0.0.0/8, ::1), "+
|
||||
"RFC1918 private (10/8, 172.16/12, 192.168/16) and link-local (169.254/16, fe80::/10) "+
|
||||
"addresses are accepted",
|
||||
zcBaseURL, host)
|
||||
}
|
||||
|
||||
// Build a fresh URL from validated components only — the IP literal,
|
||||
|
||||
Reference in New Issue
Block a user