Skip to content

Commit

Permalink
Don't configure IPv6 addr/gw when IPv6 disabled.
Browse files Browse the repository at this point in the history
When IPv6 is disabled in a container by, for example, using the --sysctl
option - an IPv6 address/gateway is still allocated. Don't attempt to
apply that config because doing so enables IPv6 on the interface.

Signed-off-by: Rob Murray <rob.murray@docker.com>
  • Loading branch information
robmry committed Mar 6, 2024
1 parent 4e53936 commit ef5295c
Show file tree
Hide file tree
Showing 2 changed files with 79 additions and 3 deletions.
67 changes: 67 additions & 0 deletions integration/networking/bridge_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ package networking
import (
"context"
"fmt"
"regexp"
"testing"
"time"

Expand All @@ -12,6 +13,7 @@ import (
"github.com/docker/docker/integration/internal/network"
"github.com/docker/docker/testutil"
"github.com/docker/docker/testutil/daemon"
"github.com/google/go-cmp/cmp/cmpopts"
"gotest.tools/v3/assert"
is "gotest.tools/v3/assert/cmp"
"gotest.tools/v3/skip"
Expand Down Expand Up @@ -594,3 +596,68 @@ func TestInternalNwConnectivity(t *testing.T) {
assert.Check(t, is.Equal(res.ExitCode, 1))
assert.Check(t, is.Contains(res.Stderr(), "Network is unreachable"))
}

// Check that the container's interface has no IPv6 address when IPv6 is
// disabled in a container via sysctl.
func TestDisableIPv6Addrs(t *testing.T) {
skip.If(t, testEnv.DaemonInfo.OSType == "windows")

ctx := setupTest(t)
d := daemon.New(t)
d.StartWithBusybox(ctx, t)
defer d.Stop(t)

c := d.NewClientT(t)
defer c.Close()

testcases := []struct {
name string
sysctls map[string]string
expIPv6 bool
}{
{
name: "IPv6 enabled",
expIPv6: true,
},
{
name: "IPv6 disabled",
sysctls: map[string]string{"net.ipv6.conf.all.disable_ipv6": "1"},
},
}

const netName = "testnet"
network.CreateNoError(ctx, t, c, netName,
network.WithIPv6(),
network.WithIPAM("fda0:ef3d:6430:abcd::/64", "fda0:ef3d:6430:abcd::1"),
)
defer network.RemoveNoError(ctx, t, c, netName)

inet6RE := regexp.MustCompile(`inet6[ \t]+[0-9a-f:]*`)

for _, tc := range testcases {
t.Run(tc.name, func(t *testing.T) {
ctx := testutil.StartSpan(ctx, t)

opts := []func(config *container.TestContainerConfig){
container.WithCmd("ip", "a"),
container.WithNetworkMode(netName),
}
if len(tc.sysctls) > 0 {
opts = append(opts, container.WithSysctls(tc.sysctls))
}

runRes := container.RunAttach(ctx, t, c, opts...)
defer c.ContainerRemove(ctx, runRes.ContainerID,
containertypes.RemoveOptions{Force: true},
)

stdout := runRes.Stdout.String()
inet6 := inet6RE.FindAllString(stdout, -1)
if tc.expIPv6 {
assert.Check(t, len(inet6) > 0, "Expected IPv6 addresses but found none.")
} else {
assert.Check(t, is.DeepEqual(inet6, []string{}, cmpopts.EquateEmpty()))
}
})
}
}
15 changes: 12 additions & 3 deletions libnetwork/sandbox_linux.go
Original file line number Diff line number Diff line change
Expand Up @@ -90,8 +90,12 @@ func (sb *Sandbox) updateGateway(ep *Endpoint) error {
return fmt.Errorf("failed to set gateway while updating gateway: %v", err)
}

if err := osSbox.SetGatewayIPv6(joinInfo.gw6); err != nil {
return fmt.Errorf("failed to set IPv6 gateway while updating gateway: %v", err)
// If IPv6 has been disabled in the sandbox a gateway may still have been
// configured, don't attempt to apply it.
if ipv6, ok := sb.ipv6Enabled(); !ok || ipv6 {
if err := osSbox.SetGatewayIPv6(joinInfo.gw6); err != nil {
return fmt.Errorf("failed to set IPv6 gateway while updating gateway: %v", err)
}
}

return nil
Expand Down Expand Up @@ -279,7 +283,12 @@ func (sb *Sandbox) populateNetworkResources(ep *Endpoint) error {

ifaceOptions = append(ifaceOptions, osl.WithIPv4Address(i.addr), osl.WithRoutes(i.routes))
if i.addrv6 != nil && i.addrv6.IP.To16() != nil {
ifaceOptions = append(ifaceOptions, osl.WithIPv6Address(i.addrv6))
// If IPv6 has been disabled in the Sandbox, an IPv6 address will still have
// been allocated. Don't apply it, because doing so would enable IPv6 on the
// interface.
if ipv6, ok := sb.ipv6Enabled(); !ok || ipv6 {
ifaceOptions = append(ifaceOptions, osl.WithIPv6Address(i.addrv6))
}
}
if len(i.llAddrs) != 0 {
ifaceOptions = append(ifaceOptions, osl.WithLinkLocalAddresses(i.llAddrs))
Expand Down

0 comments on commit ef5295c

Please sign in to comment.