Change the types for IP address and prefix struct fields to netip.Addr
and netip.Prefix for convenience. Fields such as
swarm.InitRequest.ListenAddr which may encode non-numeric values such as
a network interface name have not been modified.
Signed-off-by: Cory Snider <csnider@mirantis.com>
| ... | ... |
@@ -1,6 +1,7 @@ |
| 1 | 1 |
package swarm |
| 2 | 2 |
|
| 3 | 3 |
import ( |
| 4 |
+ "net/netip" |
|
| 4 | 5 |
"time" |
| 5 | 6 |
|
| 6 | 7 |
"github.com/moby/moby/api/types/container" |
| ... | ... |
@@ -14,7 +15,7 @@ import ( |
| 14 | 14 |
// TODO: `domain` is not supported yet. |
| 15 | 15 |
type DNSConfig struct {
|
| 16 | 16 |
// Nameservers specifies the IP addresses of the name servers |
| 17 |
- Nameservers []string `json:",omitempty"` |
|
| 17 |
+ Nameservers []netip.Addr `json:",omitempty"` |
|
| 18 | 18 |
// Search specifies the search list for host-name lookup |
| 19 | 19 |
Search []string `json:",omitempty"` |
| 20 | 20 |
// Options allows certain internal resolver variables to be modified |
| ... | ... |
@@ -1,6 +1,8 @@ |
| 1 | 1 |
package swarm |
| 2 | 2 |
|
| 3 | 3 |
import ( |
| 4 |
+ "net/netip" |
|
| 5 |
+ |
|
| 4 | 6 |
"github.com/moby/moby/api/types/network" |
| 5 | 7 |
) |
| 6 | 8 |
|
| ... | ... |
@@ -68,8 +70,8 @@ const ( |
| 68 | 68 |
|
| 69 | 69 |
// EndpointVirtualIP represents the virtual ip of a port. |
| 70 | 70 |
type EndpointVirtualIP struct {
|
| 71 |
- NetworkID string `json:",omitempty"` |
|
| 72 |
- Addr string `json:",omitempty"` |
|
| 71 |
+ NetworkID string `json:",omitempty"` |
|
| 72 |
+ Addr netip.Addr `json:",omitempty"` |
|
| 73 | 73 |
} |
| 74 | 74 |
|
| 75 | 75 |
// Network represents a network. |
| ... | ... |
@@ -103,8 +105,8 @@ type NetworkAttachmentConfig struct {
|
| 103 | 103 |
|
| 104 | 104 |
// NetworkAttachment represents a network attachment. |
| 105 | 105 |
type NetworkAttachment struct {
|
| 106 |
- Network Network `json:",omitempty"` |
|
| 107 |
- Addresses []string `json:",omitempty"` |
|
| 106 |
+ Network Network `json:",omitempty"` |
|
| 107 |
+ Addresses []netip.Addr `json:",omitempty"` |
|
| 108 | 108 |
} |
| 109 | 109 |
|
| 110 | 110 |
// IPAMOptions represents ipam options. |
| ... | ... |
@@ -115,7 +117,7 @@ type IPAMOptions struct {
|
| 115 | 115 |
|
| 116 | 116 |
// IPAMConfig represents ipam configuration. |
| 117 | 117 |
type IPAMConfig struct {
|
| 118 |
- Subnet string `json:",omitempty"` |
|
| 119 |
- Range string `json:",omitempty"` |
|
| 120 |
- Gateway string `json:",omitempty"` |
|
| 118 |
+ Subnet netip.Prefix `json:",omitempty"` |
|
| 119 |
+ Range netip.Prefix `json:",omitempty"` |
|
| 120 |
+ Gateway netip.Addr `json:",omitempty"` |
|
| 121 | 121 |
} |
| ... | ... |
@@ -1,6 +1,7 @@ |
| 1 | 1 |
package swarm |
| 2 | 2 |
|
| 3 | 3 |
import ( |
| 4 |
+ "net/netip" |
|
| 4 | 5 |
"time" |
| 5 | 6 |
) |
| 6 | 7 |
|
| ... | ... |
@@ -12,7 +13,7 @@ type ClusterInfo struct {
|
| 12 | 12 |
Spec Spec |
| 13 | 13 |
TLSInfo TLSInfo |
| 14 | 14 |
RootRotationInProgress bool |
| 15 |
- DefaultAddrPool []string |
|
| 15 |
+ DefaultAddrPool []netip.Prefix |
|
| 16 | 16 |
SubnetSize uint32 |
| 17 | 17 |
DataPathPort uint32 |
| 18 | 18 |
} |
| ... | ... |
@@ -159,7 +160,7 @@ type InitRequest struct {
|
| 159 | 159 |
Spec Spec |
| 160 | 160 |
AutoLockManagers bool |
| 161 | 161 |
Availability NodeAvailability |
| 162 |
- DefaultAddrPool []string |
|
| 162 |
+ DefaultAddrPool []netip.Prefix |
|
| 163 | 163 |
SubnetSize uint32 |
| 164 | 164 |
} |
| 165 | 165 |
|
| ... | ... |
@@ -4,6 +4,7 @@ import ( |
| 4 | 4 |
"context" |
| 5 | 5 |
"encoding/json" |
| 6 | 6 |
"fmt" |
| 7 |
+ "net/netip" |
|
| 7 | 8 |
"strings" |
| 8 | 9 |
|
| 9 | 10 |
"github.com/containerd/log" |
| ... | ... |
@@ -11,6 +12,7 @@ import ( |
| 11 | 11 |
"github.com/moby/moby/api/types/container" |
| 12 | 12 |
mounttypes "github.com/moby/moby/api/types/mount" |
| 13 | 13 |
types "github.com/moby/moby/api/types/swarm" |
| 14 |
+ "github.com/moby/moby/v2/daemon/internal/sliceutil" |
|
| 14 | 15 |
swarmapi "github.com/moby/swarmkit/v2/api" |
| 15 | 16 |
"github.com/pkg/errors" |
| 16 | 17 |
) |
| ... | ... |
@@ -47,7 +49,7 @@ func containerSpecFromGRPC(c *swarmapi.ContainerSpec) *types.ContainerSpec {
|
| 47 | 47 |
|
| 48 | 48 |
if c.DNSConfig != nil {
|
| 49 | 49 |
containerSpec.DNSConfig = &types.DNSConfig{
|
| 50 |
- Nameservers: c.DNSConfig.Nameservers, |
|
| 50 |
+ Nameservers: sliceutil.Map(c.DNSConfig.Nameservers, func(s string) netip.Addr { a, _ := netip.ParseAddr(s); return a }),
|
|
| 51 | 51 |
Search: c.DNSConfig.Search, |
| 52 | 52 |
Options: c.DNSConfig.Options, |
| 53 | 53 |
} |
| ... | ... |
@@ -309,7 +311,7 @@ func containerToGRPC(c *types.ContainerSpec) (*swarmapi.ContainerSpec, error) {
|
| 309 | 309 |
|
| 310 | 310 |
if c.DNSConfig != nil {
|
| 311 | 311 |
containerSpec.DNSConfig = &swarmapi.ContainerSpec_DNSConfig{
|
| 312 |
- Nameservers: c.DNSConfig.Nameservers, |
|
| 312 |
+ Nameservers: sliceutil.Map(c.DNSConfig.Nameservers, (netip.Addr).String), |
|
| 313 | 313 |
Search: c.DNSConfig.Search, |
| 314 | 314 |
Options: c.DNSConfig.Options, |
| 315 | 315 |
} |
| ... | ... |
@@ -1,6 +1,7 @@ |
| 1 | 1 |
package convert |
| 2 | 2 |
|
| 3 | 3 |
import ( |
| 4 |
+ "net/netip" |
|
| 4 | 5 |
"strings" |
| 5 | 6 |
"time" |
| 6 | 7 |
|
| ... | ... |
@@ -8,6 +9,8 @@ import ( |
| 8 | 8 |
"github.com/moby/moby/api/types/network" |
| 9 | 9 |
types "github.com/moby/moby/api/types/swarm" |
| 10 | 10 |
"github.com/moby/moby/v2/daemon/cluster/convert/netextra" |
| 11 |
+ "github.com/moby/moby/v2/daemon/internal/netiputil" |
|
| 12 |
+ "github.com/moby/moby/v2/daemon/internal/sliceutil" |
|
| 11 | 13 |
"github.com/moby/moby/v2/daemon/libnetwork/scope" |
| 12 | 14 |
swarmapi "github.com/moby/swarmkit/v2/api" |
| 13 | 15 |
) |
| ... | ... |
@@ -16,7 +19,7 @@ func networkAttachmentFromGRPC(na *swarmapi.NetworkAttachment) types.NetworkAtta |
| 16 | 16 |
if na != nil {
|
| 17 | 17 |
return types.NetworkAttachment{
|
| 18 | 18 |
Network: networkFromGRPC(na.Network), |
| 19 |
- Addresses: na.Addresses, |
|
| 19 |
+ Addresses: sliceutil.Map(na.Addresses, func(s string) netip.Addr { a, _ := netip.ParseAddr(s); return a }),
|
|
| 20 | 20 |
} |
| 21 | 21 |
} |
| 22 | 22 |
return types.NetworkAttachment{}
|
| ... | ... |
@@ -82,10 +85,16 @@ func ipamFromGRPC(i *swarmapi.IPAMOptions) *types.IPAMOptions {
|
| 82 | 82 |
} |
| 83 | 83 |
|
| 84 | 84 |
for _, config := range i.Configs {
|
| 85 |
+ // Best-effort parse of user suppplied values that have |
|
| 86 |
+ // been round-tripped through Swarm's Raft store. It is |
|
| 87 |
+ // far too late to reject bogus values. |
|
| 88 |
+ subnet, _ := netiputil.ParseCIDR(config.Subnet) |
|
| 89 |
+ iprange, _ := netiputil.ParseCIDR(config.Range) |
|
| 90 |
+ gw, _ := netip.ParseAddr(config.Gateway) |
|
| 85 | 91 |
ipam.Configs = append(ipam.Configs, types.IPAMConfig{
|
| 86 |
- Subnet: config.Subnet, |
|
| 87 |
- Range: config.Range, |
|
| 88 |
- Gateway: config.Gateway, |
|
| 92 |
+ Subnet: subnet.Masked(), |
|
| 93 |
+ Range: iprange.Masked(), |
|
| 94 |
+ Gateway: gw.Unmap(), |
|
| 89 | 95 |
}) |
| 90 | 96 |
} |
| 91 | 97 |
} |
| ... | ... |
@@ -118,9 +127,10 @@ func endpointFromGRPC(e *swarmapi.Endpoint) types.Endpoint {
|
| 118 | 118 |
} |
| 119 | 119 |
|
| 120 | 120 |
for _, v := range e.VirtualIPs {
|
| 121 |
+ vip, _ := netip.ParseAddr(v.Addr) |
|
| 121 | 122 |
endpoint.VirtualIPs = append(endpoint.VirtualIPs, types.EndpointVirtualIP{
|
| 122 | 123 |
NetworkID: v.NetworkID, |
| 123 |
- Addr: v.Addr, |
|
| 124 |
+ Addr: vip, |
|
| 124 | 125 |
}) |
| 125 | 126 |
} |
| 126 | 127 |
} |
| ... | ... |
@@ -2,10 +2,12 @@ package convert |
| 2 | 2 |
|
| 3 | 3 |
import ( |
| 4 | 4 |
"fmt" |
| 5 |
+ "net/netip" |
|
| 5 | 6 |
"strings" |
| 6 | 7 |
|
| 7 | 8 |
gogotypes "github.com/gogo/protobuf/types" |
| 8 | 9 |
types "github.com/moby/moby/api/types/swarm" |
| 10 |
+ "github.com/moby/moby/v2/daemon/internal/sliceutil" |
|
| 9 | 11 |
swarmapi "github.com/moby/swarmkit/v2/api" |
| 10 | 12 |
"github.com/moby/swarmkit/v2/ca" |
| 11 | 13 |
) |
| ... | ... |
@@ -40,7 +42,7 @@ func SwarmFromGRPC(c swarmapi.Cluster) types.Swarm {
|
| 40 | 40 |
TrustRoot: string(c.RootCA.CACert), |
| 41 | 41 |
}, |
| 42 | 42 |
RootRotationInProgress: c.RootCA.RootRotation != nil, |
| 43 |
- DefaultAddrPool: c.DefaultAddressPool, |
|
| 43 |
+ DefaultAddrPool: sliceutil.Map(c.DefaultAddressPool, func(s string) netip.Prefix { pfx, _ := netip.ParsePrefix(s); return pfx }),
|
|
| 44 | 44 |
SubnetSize: c.SubnetSize, |
| 45 | 45 |
DataPathPort: c.VXLANUDPPort, |
| 46 | 46 |
}, |
| ... | ... |
@@ -4,7 +4,7 @@ import ( |
| 4 | 4 |
"errors" |
| 5 | 5 |
"fmt" |
| 6 | 6 |
"net" |
| 7 |
- "strings" |
|
| 7 |
+ "net/netip" |
|
| 8 | 8 |
) |
| 9 | 9 |
|
| 10 | 10 |
const ( |
| ... | ... |
@@ -91,7 +91,7 @@ func (c *Cluster) resolveAdvertiseAddr(advertiseAddr, listenAddrPort string) (st |
| 91 | 91 |
|
| 92 | 92 |
// validateDefaultAddrPool validates default address pool |
| 93 | 93 |
// it also strips white space from the string before validation |
| 94 |
-func validateDefaultAddrPool(defaultAddrPool []string, size uint32) error {
|
|
| 94 |
+func validateDefaultAddrPool(defaultAddrPool []netip.Prefix, size uint32) error {
|
|
| 95 | 95 |
if defaultAddrPool == nil {
|
| 96 | 96 |
// defaultAddrPool is not defined |
| 97 | 97 |
return nil |
| ... | ... |
@@ -108,16 +108,9 @@ func validateDefaultAddrPool(defaultAddrPool []string, size uint32) error {
|
| 108 | 108 |
if size > 29 {
|
| 109 | 109 |
return fmt.Errorf("subnet size is out of range: %d", size)
|
| 110 | 110 |
} |
| 111 |
- for i := range defaultAddrPool {
|
|
| 112 |
- // trim leading and trailing white spaces |
|
| 113 |
- defaultAddrPool[i] = strings.TrimSpace(defaultAddrPool[i]) |
|
| 114 |
- _, b, err := net.ParseCIDR(defaultAddrPool[i]) |
|
| 115 |
- if err != nil {
|
|
| 116 |
- return fmt.Errorf("invalid base pool %s: %v", defaultAddrPool[i], err)
|
|
| 117 |
- } |
|
| 118 |
- ones, _ := b.Mask.Size() |
|
| 119 |
- if size < uint32(ones) {
|
|
| 120 |
- return fmt.Errorf("invalid CIDR: %q. Subnet size is too small for pool: %d", defaultAddrPool[i], size)
|
|
| 111 |
+ for _, a := range defaultAddrPool {
|
|
| 112 |
+ if size < uint32(a.Bits()) {
|
|
| 113 |
+ return fmt.Errorf("invalid CIDR: %q. Subnet size is too small for pool: %d", a, size)
|
|
| 121 | 114 |
} |
| 122 | 115 |
} |
| 123 | 116 |
|
| ... | ... |
@@ -3,6 +3,7 @@ package cluster |
| 3 | 3 |
import ( |
| 4 | 4 |
"context" |
| 5 | 5 |
"fmt" |
| 6 |
+ "net/netip" |
|
| 6 | 7 |
"path/filepath" |
| 7 | 8 |
"strings" |
| 8 | 9 |
"sync" |
| ... | ... |
@@ -12,6 +13,7 @@ import ( |
| 12 | 12 |
types "github.com/moby/moby/api/types/swarm" |
| 13 | 13 |
"github.com/moby/moby/v2/daemon/cluster/convert" |
| 14 | 14 |
"github.com/moby/moby/v2/daemon/cluster/executor/container" |
| 15 |
+ "github.com/moby/moby/v2/daemon/internal/sliceutil" |
|
| 15 | 16 |
lncluster "github.com/moby/moby/v2/daemon/libnetwork/cluster" |
| 16 | 17 |
"github.com/moby/moby/v2/daemon/libnetwork/cnmallocator" |
| 17 | 18 |
swarmapi "github.com/moby/swarmkit/v2/api" |
| ... | ... |
@@ -55,7 +57,7 @@ type nodeStartConfig struct {
|
| 55 | 55 |
// DataPathAddr is the address that has to be used for the data path |
| 56 | 56 |
DataPathAddr string |
| 57 | 57 |
// DefaultAddressPool contains list of subnets |
| 58 |
- DefaultAddressPool []string |
|
| 58 |
+ DefaultAddressPool []netip.Prefix |
|
| 59 | 59 |
// SubnetSize contains subnet size of DefaultAddressPool |
| 60 | 60 |
SubnetSize uint32 |
| 61 | 61 |
// DataPathPort contains Data path port (VXLAN UDP port) number that is used for data traffic. |
| ... | ... |
@@ -126,7 +128,7 @@ func (n *nodeRunner) start(conf nodeStartConfig) error {
|
| 126 | 126 |
ListenRemoteAPI: conf.ListenAddr, |
| 127 | 127 |
AdvertiseRemoteAPI: conf.AdvertiseAddr, |
| 128 | 128 |
NetworkConfig: &networkallocator.Config{
|
| 129 |
- DefaultAddrPool: conf.DefaultAddressPool, |
|
| 129 |
+ DefaultAddrPool: sliceutil.Map(conf.DefaultAddressPool, (netip.Prefix).String), |
|
| 130 | 130 |
SubnetSize: conf.SubnetSize, |
| 131 | 131 |
VXLANUDPPort: conf.DataPathPort, |
| 132 | 132 |
}, |
| ... | ... |
@@ -21,6 +21,9 @@ func ToIPNet(p netip.Prefix) *net.IPNet {
|
| 21 | 21 |
// ToPrefix converts n into a netip.Prefix. If n is not a valid IPv4 or IPV6 |
| 22 | 22 |
// address, ToPrefix returns netip.Prefix{}, false.
|
| 23 | 23 |
func ToPrefix(n *net.IPNet) (netip.Prefix, bool) {
|
| 24 |
+ if n == nil {
|
|
| 25 |
+ return netip.Prefix{}, false
|
|
| 26 |
+ } |
|
| 24 | 27 |
if ll := len(n.Mask); ll != net.IPv4len && ll != net.IPv6len {
|
| 25 | 28 |
return netip.Prefix{}, false
|
| 26 | 29 |
} |
| ... | ... |
@@ -88,3 +91,21 @@ func PrefixAfter(prev netip.Prefix, sz int) netip.Prefix {
|
| 88 | 88 |
} |
| 89 | 89 |
return netip.PrefixFrom(addr, sz).Masked() |
| 90 | 90 |
} |
| 91 |
+ |
|
| 92 |
+// Unmap returns p with any IPv4-mapped IPv6 address prefix removed, per the |
|
| 93 |
+// quirky semantics that have been Hyrum's Law'ed into our Engine API contract: |
|
| 94 |
+// the subnet mask is truncated to the length of the unmapped address. |
|
| 95 |
+// For example: |
|
| 96 |
+// - "::ffff:1.2.3.4/24" -> 1.2.3.4/0 |
|
| 97 |
+// - "::ffff:1.2.3.4/120" -> 1.2.3.4/24 |
|
| 98 |
+func Unmap(p netip.Prefix) netip.Prefix {
|
|
| 99 |
+ bits := p.Addr().Unmap().BitLen() - p.Addr().BitLen() + p.Bits() |
|
| 100 |
+ return netip.PrefixFrom(p.Addr().Unmap(), max(0, bits)) |
|
| 101 |
+} |
|
| 102 |
+ |
|
| 103 |
+// ParseCIDR parses s as an IP address prefix, like [netip.ParsePrefix], |
|
| 104 |
+// unmapping any IPv4-mapped IPv6 address prefixes using [Unmap]. |
|
| 105 |
+func ParseCIDR(s string) (netip.Prefix, error) {
|
|
| 106 |
+ prefix, err := netip.ParsePrefix(s) |
|
| 107 |
+ return Unmap(prefix), err |
|
| 108 |
+} |
| ... | ... |
@@ -1,6 +1,7 @@ |
| 1 | 1 |
package netiputil |
| 2 | 2 |
|
| 3 | 3 |
import ( |
| 4 |
+ "net" |
|
| 4 | 5 |
"net/netip" |
| 5 | 6 |
"testing" |
| 6 | 7 |
|
| ... | ... |
@@ -44,3 +45,28 @@ func TestPrefixAfter(t *testing.T) {
|
| 44 | 44 |
assert.Check(t, next == tc.want, "PrefixAfter(%q, %d) = %s; want: %s", tc.prev, tc.sz, next, tc.want) |
| 45 | 45 |
} |
| 46 | 46 |
} |
| 47 |
+ |
|
| 48 |
+func TestUnmap(t *testing.T) {
|
|
| 49 |
+ assert.Check(t, !Unmap(netip.Prefix{}).IsValid())
|
|
| 50 |
+} |
|
| 51 |
+ |
|
| 52 |
+func TestParseCIDR(t *testing.T) {
|
|
| 53 |
+ tests := []string{"::ffff:1.2.3.4/24", "::ffff:1.2.3.4/1", "::ffff:1.2.3.4/120", "1.2.3.4/24", "::1/128", "2001:db8::/32"}
|
|
| 54 |
+ for _, s := range tests {
|
|
| 55 |
+ // From "github.com/moby/moby/v2/daemon/libnetwork/types".ParseCIDR |
|
| 56 |
+ ip, net, err := net.ParseCIDR(s) |
|
| 57 |
+ assert.NilError(t, err) |
|
| 58 |
+ net.IP = ip |
|
| 59 |
+ want := netip.MustParsePrefix(net.String()) |
|
| 60 |
+ |
|
| 61 |
+ got, err := ParseCIDR(s) |
|
| 62 |
+ assert.Check(t, err) |
|
| 63 |
+ if got != want {
|
|
| 64 |
+ t.Errorf("ParseCIDR(%q) = %v, want %v", s, got, want)
|
|
| 65 |
+ } |
|
| 66 |
+ } |
|
| 67 |
+ |
|
| 68 |
+ got, err := ParseCIDR("invalid")
|
|
| 69 |
+ assert.Check(t, err != nil, "expected error for invalid input") |
|
| 70 |
+ assert.Check(t, !got.IsValid(), "expected invalid result for invalid input") |
|
| 71 |
+} |
| ... | ... |
@@ -2,6 +2,7 @@ package network |
| 2 | 2 |
|
| 3 | 3 |
import ( |
| 4 | 4 |
"context" |
| 5 |
+ "net/netip" |
|
| 5 | 6 |
"strings" |
| 6 | 7 |
"testing" |
| 7 | 8 |
"time" |
| ... | ... |
@@ -417,7 +418,7 @@ func TestServiceWithDefaultAddressPoolInit(t *testing.T) {
|
| 417 | 417 |
ctx := setupTest(t) |
| 418 | 418 |
|
| 419 | 419 |
d := swarm.NewSwarm(ctx, t, testEnv, |
| 420 |
- daemon.WithSwarmDefaultAddrPool([]string{"20.20.0.0/16"}),
|
|
| 420 |
+ daemon.WithSwarmDefaultAddrPool(netip.MustParsePrefix("20.20.0.0/16")),
|
|
| 421 | 421 |
daemon.WithSwarmDefaultAddrPoolSubnetSize(24)) |
| 422 | 422 |
defer d.Stop(t) |
| 423 | 423 |
cli := d.NewClientT(t) |
| ... | ... |
@@ -1,10 +1,12 @@ |
| 1 | 1 |
package service |
| 2 | 2 |
|
| 3 | 3 |
import ( |
| 4 |
+ "net/netip" |
|
| 4 | 5 |
"testing" |
| 5 | 6 |
"time" |
| 6 | 7 |
|
| 7 | 8 |
"github.com/google/go-cmp/cmp" |
| 9 |
+ "github.com/google/go-cmp/cmp/cmpopts" |
|
| 8 | 10 |
"github.com/moby/moby/api/types/container" |
| 9 | 11 |
swarmtypes "github.com/moby/moby/api/types/swarm" |
| 10 | 12 |
"github.com/moby/moby/client" |
| ... | ... |
@@ -67,7 +69,10 @@ func cmpServiceOpts() cmp.Option {
|
| 67 | 67 |
return delta < threshold && delta > -threshold |
| 68 | 68 |
}) |
| 69 | 69 |
|
| 70 |
- return cmp.FilterPath(metaTimeFields, withinThreshold) |
|
| 70 |
+ return cmp.Options{
|
|
| 71 |
+ cmp.FilterPath(metaTimeFields, withinThreshold), |
|
| 72 |
+ cmpopts.EquateComparable(netip.Addr{}, netip.Prefix{}),
|
|
| 73 |
+ } |
|
| 71 | 74 |
} |
| 72 | 75 |
|
| 73 | 76 |
func fullSwarmServiceSpec(name string, replicas uint64) swarmtypes.ServiceSpec {
|
| ... | ... |
@@ -95,7 +100,7 @@ func fullSwarmServiceSpec(name string, replicas uint64) swarmtypes.ServiceSpec {
|
| 95 | 95 |
StopGracePeriod: &restartDelay, |
| 96 | 96 |
Hosts: []string{"8.8.8.8 google"},
|
| 97 | 97 |
DNSConfig: &swarmtypes.DNSConfig{
|
| 98 |
- Nameservers: []string{"8.8.8.8"},
|
|
| 98 |
+ Nameservers: []netip.Addr{netip.MustParseAddr("8.8.8.8")},
|
|
| 99 | 99 |
Search: []string{"somedomain"},
|
| 100 | 100 |
}, |
| 101 | 101 |
Isolation: container.IsolationDefault, |
| ... | ... |
@@ -7,6 +7,7 @@ import ( |
| 7 | 7 |
"fmt" |
| 8 | 8 |
"io" |
| 9 | 9 |
"net/http" |
| 10 |
+ "net/netip" |
|
| 10 | 11 |
"os" |
| 11 | 12 |
"os/exec" |
| 12 | 13 |
"os/user" |
| ... | ... |
@@ -96,7 +97,7 @@ type Daemon struct {
|
| 96 | 96 |
swarmListenAddr string |
| 97 | 97 |
swarmWithIptables bool |
| 98 | 98 |
SwarmPort int // FIXME(vdemeester) should probably not be exported |
| 99 |
- DefaultAddrPool []string |
|
| 99 |
+ DefaultAddrPool []netip.Prefix |
|
| 100 | 100 |
SubnetSize uint32 |
| 101 | 101 |
DataPathPort uint32 |
| 102 | 102 |
OOMScoreAdjust int |
| ... | ... |
@@ -1,6 +1,7 @@ |
| 1 | 1 |
package daemon |
| 2 | 2 |
|
| 3 | 3 |
import ( |
| 4 |
+ "net/netip" |
|
| 4 | 5 |
"os/user" |
| 5 | 6 |
|
| 6 | 7 |
"github.com/moby/moby/v2/internal/testutil/environment" |
| ... | ... |
@@ -82,7 +83,7 @@ func WithSwarmIptables(useIptables bool) Option {
|
| 82 | 82 |
} |
| 83 | 83 |
|
| 84 | 84 |
// WithSwarmDefaultAddrPool sets the swarm default address pool to use for swarm mode |
| 85 |
-func WithSwarmDefaultAddrPool(defaultAddrPool []string) Option {
|
|
| 85 |
+func WithSwarmDefaultAddrPool(defaultAddrPool ...netip.Prefix) Option {
|
|
| 86 | 86 |
return func(d *Daemon) {
|
| 87 | 87 |
d.DefaultAddrPool = defaultAddrPool |
| 88 | 88 |
} |
| ... | ... |
@@ -1,6 +1,7 @@ |
| 1 | 1 |
package swarm |
| 2 | 2 |
|
| 3 | 3 |
import ( |
| 4 |
+ "net/netip" |
|
| 4 | 5 |
"time" |
| 5 | 6 |
|
| 6 | 7 |
"github.com/moby/moby/api/types/container" |
| ... | ... |
@@ -14,7 +15,7 @@ import ( |
| 14 | 14 |
// TODO: `domain` is not supported yet. |
| 15 | 15 |
type DNSConfig struct {
|
| 16 | 16 |
// Nameservers specifies the IP addresses of the name servers |
| 17 |
- Nameservers []string `json:",omitempty"` |
|
| 17 |
+ Nameservers []netip.Addr `json:",omitempty"` |
|
| 18 | 18 |
// Search specifies the search list for host-name lookup |
| 19 | 19 |
Search []string `json:",omitempty"` |
| 20 | 20 |
// Options allows certain internal resolver variables to be modified |
| ... | ... |
@@ -1,6 +1,8 @@ |
| 1 | 1 |
package swarm |
| 2 | 2 |
|
| 3 | 3 |
import ( |
| 4 |
+ "net/netip" |
|
| 5 |
+ |
|
| 4 | 6 |
"github.com/moby/moby/api/types/network" |
| 5 | 7 |
) |
| 6 | 8 |
|
| ... | ... |
@@ -68,8 +70,8 @@ const ( |
| 68 | 68 |
|
| 69 | 69 |
// EndpointVirtualIP represents the virtual ip of a port. |
| 70 | 70 |
type EndpointVirtualIP struct {
|
| 71 |
- NetworkID string `json:",omitempty"` |
|
| 72 |
- Addr string `json:",omitempty"` |
|
| 71 |
+ NetworkID string `json:",omitempty"` |
|
| 72 |
+ Addr netip.Addr `json:",omitempty"` |
|
| 73 | 73 |
} |
| 74 | 74 |
|
| 75 | 75 |
// Network represents a network. |
| ... | ... |
@@ -103,8 +105,8 @@ type NetworkAttachmentConfig struct {
|
| 103 | 103 |
|
| 104 | 104 |
// NetworkAttachment represents a network attachment. |
| 105 | 105 |
type NetworkAttachment struct {
|
| 106 |
- Network Network `json:",omitempty"` |
|
| 107 |
- Addresses []string `json:",omitempty"` |
|
| 106 |
+ Network Network `json:",omitempty"` |
|
| 107 |
+ Addresses []netip.Addr `json:",omitempty"` |
|
| 108 | 108 |
} |
| 109 | 109 |
|
| 110 | 110 |
// IPAMOptions represents ipam options. |
| ... | ... |
@@ -115,7 +117,7 @@ type IPAMOptions struct {
|
| 115 | 115 |
|
| 116 | 116 |
// IPAMConfig represents ipam configuration. |
| 117 | 117 |
type IPAMConfig struct {
|
| 118 |
- Subnet string `json:",omitempty"` |
|
| 119 |
- Range string `json:",omitempty"` |
|
| 120 |
- Gateway string `json:",omitempty"` |
|
| 118 |
+ Subnet netip.Prefix `json:",omitempty"` |
|
| 119 |
+ Range netip.Prefix `json:",omitempty"` |
|
| 120 |
+ Gateway netip.Addr `json:",omitempty"` |
|
| 121 | 121 |
} |
| ... | ... |
@@ -1,6 +1,7 @@ |
| 1 | 1 |
package swarm |
| 2 | 2 |
|
| 3 | 3 |
import ( |
| 4 |
+ "net/netip" |
|
| 4 | 5 |
"time" |
| 5 | 6 |
) |
| 6 | 7 |
|
| ... | ... |
@@ -12,7 +13,7 @@ type ClusterInfo struct {
|
| 12 | 12 |
Spec Spec |
| 13 | 13 |
TLSInfo TLSInfo |
| 14 | 14 |
RootRotationInProgress bool |
| 15 |
- DefaultAddrPool []string |
|
| 15 |
+ DefaultAddrPool []netip.Prefix |
|
| 16 | 16 |
SubnetSize uint32 |
| 17 | 17 |
DataPathPort uint32 |
| 18 | 18 |
} |
| ... | ... |
@@ -159,7 +160,7 @@ type InitRequest struct {
|
| 159 | 159 |
Spec Spec |
| 160 | 160 |
AutoLockManagers bool |
| 161 | 161 |
Availability NodeAvailability |
| 162 |
- DefaultAddrPool []string |
|
| 162 |
+ DefaultAddrPool []netip.Prefix |
|
| 163 | 163 |
SubnetSize uint32 |
| 164 | 164 |
} |
| 165 | 165 |
|