summaryrefslogtreecommitdiff
path: root/caddyconfig
diff options
context:
space:
mode:
authorMichael Stapelberg <stapelberg@users.noreply.github.com>2022-09-15 16:03:24 +0200
committerGitHub <noreply@github.com>2022-09-15 08:03:24 -0600
commita1ad20e4720391d847c58fcdcef7c8d9c287faf2 (patch)
tree25c0081ddb7e978ca9bb71b245eeb1cdcfaefda2 /caddyconfig
parent62b0685375cc4dc2c670afd07d1319affa179544 (diff)
httpcaddyfile: Fix bind when IPv6 is specified with network (#4950)
* fix listening on IPv6 addresses: use net.JoinHostPort Commit 1e18afb5c862d62be130d563785de5c58f08ae8e broke my caddy setup. This commit fixes it. * Refactor solution; simplify, add descriptive comment * Move network to host, not copy Co-authored-by: Matthew Holt <mholt@users.noreply.github.com>
Diffstat (limited to 'caddyconfig')
-rw-r--r--caddyconfig/httpcaddyfile/addresses.go36
1 files changed, 24 insertions, 12 deletions
diff --git a/caddyconfig/httpcaddyfile/addresses.go b/caddyconfig/httpcaddyfile/addresses.go
index e7a7cdb..93bad27 100644
--- a/caddyconfig/httpcaddyfile/addresses.go
+++ b/caddyconfig/httpcaddyfile/addresses.go
@@ -36,12 +36,12 @@ import (
// server block that share the same address stay grouped together so the config
// isn't repeated unnecessarily. For example, this Caddyfile:
//
-// example.com {
-// bind 127.0.0.1
-// }
-// www.example.com, example.net/path, localhost:9999 {
-// bind 127.0.0.1 1.2.3.4
-// }
+// example.com {
+// bind 127.0.0.1
+// }
+// www.example.com, example.net/path, localhost:9999 {
+// bind 127.0.0.1 1.2.3.4
+// }
//
// has two server blocks to start with. But expressed in this Caddyfile are
// actually 4 listener addresses: 127.0.0.1:443, 1.2.3.4:443, 127.0.0.1:9999,
@@ -219,7 +219,7 @@ func (st *ServerType) listenerAddrsForServerBlockKey(sblock serverBlock, key str
return nil, fmt.Errorf("[%s] scheme and port violate convention", key)
}
- // the bind directive specifies hosts, but is optional
+ // the bind directive specifies hosts (and potentially network), but is optional
lnHosts := make([]string, 0, len(sblock.pile["bind"]))
for _, cfgVal := range sblock.pile["bind"] {
lnHosts = append(lnHosts, cfgVal.Value.([]string)...)
@@ -234,11 +234,23 @@ func (st *ServerType) listenerAddrsForServerBlockKey(sblock serverBlock, key str
// use a map to prevent duplication
listeners := make(map[string]struct{})
- for _, host := range lnHosts {
- // host can have network + host (e.g. "tcp6/localhost") but
- // will/should not have port information because this usually
- // comes from the bind directive, so we append the port
- addr, err := caddy.ParseNetworkAddress(host + ":" + lnPort)
+ for _, lnHost := range lnHosts {
+ // normally we would simply append the port,
+ // but if lnHost is IPv6, we need to ensure it
+ // is enclosed in [ ]; net.JoinHostPort does
+ // this for us, but lnHost might also have a
+ // network type in front (e.g. "tcp/") leading
+ // to "[tcp/::1]" which causes parsing failures
+ // later; what we need is "tcp/[::1]", so we have
+ // to split the network and host, then re-combine
+ network, host, ok := strings.Cut(lnHost, "/")
+ if !ok {
+ host = network
+ network = ""
+ }
+ host = strings.Trim(host, "[]") // IPv6
+ networkAddr := caddy.JoinNetworkAddress(network, host, lnPort)
+ addr, err := caddy.ParseNetworkAddress(networkAddr)
if err != nil {
return nil, fmt.Errorf("parsing network address: %v", err)
}