Allocate IPv6 addresses after detecting IPv6 support#47406
Merged
robmry merged 7 commits intomoby:masterfrom Nov 5, 2024
Merged
Allocate IPv6 addresses after detecting IPv6 support#47406robmry merged 7 commits intomoby:masterfrom
robmry merged 7 commits intomoby:masterfrom
Conversation
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
- What I did
If IPv6 is disabled for a container, do not allocate an IPv6 address when it's attached to an IPv6 network.
- How I did it
There are a few commits - it's probably easiest to review them separately ...
Unconditionally update container.NetworkSettings
In
daemon.allocateNetwork(), flagupdateSettingswas set ifcontainer.NetworkSettings.Networkswas empty. That flag was passed down through the call stack to avoid a call todaemon.updateNetworkSettings()indaemon.updateNetworkConfig().Other calls to
daemon.updateNetworkSettings(), which happen when connecting an existing container to another network, unconditionally made the NetworkSettings update.I don't think there's a circumstance where NetworkSettings is not empty during container creation. Even if there is, the update is harmless and cheap. Eliminating the
updateSettingsflag simplifies the code a little and, in the next commit whereallocateNetwork()is split out ofinitializeNetworking(), it avoids the need to pass that flag between the two.Separate Sandbox/Endpoint construction
Previously, the
libnetwork.Sandboxwas created indaemon.allocateNetwork()if there was no network - otherwise it happened while connecting an Endpoint indaemon.connectToNetwork(). If there was an endpoint in the default bridge, it had to be connected first, because extra configuration is needed in the Sandbox for legacy links and that could only happen during Sandbox construction.Now, config for legacy links is added to the Sandbox when constructing the Endpoint that needs it - removing the constraint on ordering of Endpoint construction, and the dependency between Endpoint and Sandbox construction.
So, now a Sandbox can be constructed in one place, before the first Endpoint.
Also, replaces some legacy-link specific Sandbox option-setters with Sandbox methods for updating
/etc/hosts, and updates a legacy-link parent's IPv6 address as well as its IPv4 address when a child container restarts.Configure network endpoints after creating a container
This commit splits the bulk of
daemon.allocateNetwork()out ofdaemon.initializeNetworking().daemon.initializeNetworking()hasn't moved, but it now only prepares configuration and doesn't do any Endpoint construction or configuration. Sandbox construction still happens here.Endpoint construction is in
daemon.allocateNetwork()which, on non-Windows, is called after the container task has been created (before it's started).On Windows, Endpoint construction still happens before the container task is created. If it's created afterwards, some DNS lookups for the container don't seem to end up in our resolver - see the TODO comment in the code. (But, Windows can't benefit from the delayed assignment of IPv6 addresses anyway.)
Doing the Endpoint construction after the
osSboxhas been set up makes it possible to probe the container's network for IPv6 support first - enabling the next commit ...Only assign IPv6 addresses if required
If a Sandbox is provided to
CreateEndpointForSandbox, check whether it has IPv6 before allocating IPv6 addresses.Because no IPv6 address is added to the DNS when the Sandbox doesn't support it, a lookup for a container on an IPv6 network can now have no IPv6 address. The resolver is updated to treat a missing IPv6 address on an IPv4 hit as
ipv6misseven if the network has IPv6 enabled. (So, an empty DNS response is returned, avoiding the upstream DNS request and NXDOMAIN.)The
macvlandriver expected an endpoint on a network with IPv6 subnets to have an IPv6 address - it searched the subnets for the address assigned to the endpoint, to work out which gateway address to use (crashing if there was no address). Now, it only makes that search if there is an IPv6 address.- How to verify it
Existing regression tests for the refactoring.
New integration test checks that a container with IPv6 disabled via
sysctlon an IPv6 network has no IPv6 address.- Description for the changelog
If IPv6 is disabled for a container, do not allocate an IPv6 address when it's attached to an IPv6 network.