mirror of
https://github.com/moby/moby.git
synced 2022-11-09 12:21:53 -05:00
Allow specifying a default gateway for bridge networking
Signed-off-by: Sylvain Baubeau <sbaubeau@redhat.com>
This commit is contained in:
parent
b7950b725b
commit
acb6127c1a
5 changed files with 80 additions and 13 deletions
|
@ -58,6 +58,8 @@ func (config *Config) InstallFlags() {
|
|||
flag.StringVar(&config.Bridge.Iface, []string{"b", "-bridge"}, "", "Attach containers to a network bridge")
|
||||
flag.StringVar(&config.Bridge.FixedCIDR, []string{"-fixed-cidr"}, "", "IPv4 subnet for fixed IPs")
|
||||
flag.StringVar(&config.Bridge.FixedCIDRv6, []string{"-fixed-cidr-v6"}, "", "IPv6 subnet for fixed IPs")
|
||||
flag.StringVar(&config.Bridge.DefaultGatewayIPv4, []string{"-default-gateway"}, "", "Container default gateway IPv4 address")
|
||||
flag.StringVar(&config.Bridge.DefaultGatewayIPv6, []string{"-default-gateway-v6"}, "", "Container default gateway IPv6 address")
|
||||
flag.BoolVar(&config.Bridge.InterContainerCommunication, []string{"#icc", "-icc"}, true, "Enable inter-container communication")
|
||||
flag.StringVar(&config.GraphDriver, []string{"s", "-storage-driver"}, "", "Storage driver to use")
|
||||
flag.StringVar(&config.ExecDriver, []string{"e", "-exec-driver"}, "native", "Exec driver to use")
|
||||
|
|
|
@ -77,8 +77,10 @@ var (
|
|||
|
||||
bridgeIface string
|
||||
bridgeIPv4Network *net.IPNet
|
||||
gatewayIPv4 net.IP
|
||||
bridgeIPv6Addr net.IP
|
||||
globalIPv6Network *net.IPNet
|
||||
gatewayIPv6 net.IP
|
||||
portMapper *portmapper.PortMapper
|
||||
once sync.Once
|
||||
|
||||
|
@ -103,6 +105,8 @@ type Config struct {
|
|||
IP string
|
||||
FixedCIDR string
|
||||
FixedCIDRv6 string
|
||||
DefaultGatewayIPv4 string
|
||||
DefaultGatewayIPv6 string
|
||||
InterContainerCommunication bool
|
||||
}
|
||||
|
||||
|
@ -278,6 +282,12 @@ func InitDriver(config *Config) error {
|
|||
}
|
||||
}
|
||||
|
||||
if gateway, err := requestDefaultGateway(config.DefaultGatewayIPv4, bridgeIPv4Network); err != nil {
|
||||
return err
|
||||
} else {
|
||||
gatewayIPv4 = gateway
|
||||
}
|
||||
|
||||
if config.FixedCIDRv6 != "" {
|
||||
_, subnet, err := net.ParseCIDR(config.FixedCIDRv6)
|
||||
if err != nil {
|
||||
|
@ -289,6 +299,12 @@ func InitDriver(config *Config) error {
|
|||
return err
|
||||
}
|
||||
globalIPv6Network = subnet
|
||||
|
||||
if gateway, err := requestDefaultGateway(config.DefaultGatewayIPv6, globalIPv6Network); err != nil {
|
||||
return err
|
||||
} else {
|
||||
gatewayIPv6 = gateway
|
||||
}
|
||||
}
|
||||
|
||||
// Block BridgeIP in IP allocator
|
||||
|
@ -473,6 +489,24 @@ func setupIPv6Bridge(bridgeIPv6 string) error {
|
|||
return nil
|
||||
}
|
||||
|
||||
func requestDefaultGateway(requestedGateway string, network *net.IPNet) (gateway net.IP, err error) {
|
||||
if requestedGateway != "" {
|
||||
gateway = net.ParseIP(requestedGateway)
|
||||
|
||||
if gateway == nil {
|
||||
return nil, fmt.Errorf("Bad parameter: invalid gateway ip %s", requestedGateway)
|
||||
}
|
||||
|
||||
if !network.Contains(gateway) {
|
||||
return nil, fmt.Errorf("Gateway ip %s must be part of the network %s", requestedGateway, network.String())
|
||||
}
|
||||
|
||||
ipAllocator.RequestIP(network, gateway)
|
||||
}
|
||||
|
||||
return gateway, nil
|
||||
}
|
||||
|
||||
func createBridgeIface(name string) error {
|
||||
kv, err := kernel.GetKernelVersion()
|
||||
// Only set the bridge's mac address if the kernel version is > 3.3
|
||||
|
@ -522,10 +556,12 @@ func linkLocalIPv6FromMac(mac string) (string, error) {
|
|||
// Allocate a network interface
|
||||
func Allocate(id, requestedMac, requestedIP, requestedIPv6 string) (*network.Settings, error) {
|
||||
var (
|
||||
ip net.IP
|
||||
mac net.HardwareAddr
|
||||
err error
|
||||
globalIPv6 net.IP
|
||||
ip net.IP
|
||||
mac net.HardwareAddr
|
||||
err error
|
||||
globalIPv6 net.IP
|
||||
defaultGWIPv4 net.IP
|
||||
defaultGWIPv6 net.IP
|
||||
)
|
||||
|
||||
ip, err = ipAllocator.RequestIP(bridgeIPv4Network, net.ParseIP(requestedIP))
|
||||
|
@ -560,6 +596,18 @@ func Allocate(id, requestedMac, requestedIP, requestedIPv6 string) (*network.Set
|
|||
|
||||
maskSize, _ := bridgeIPv4Network.Mask.Size()
|
||||
|
||||
if gatewayIPv4 != nil {
|
||||
defaultGWIPv4 = gatewayIPv4
|
||||
} else {
|
||||
defaultGWIPv4 = bridgeIPv4Network.IP
|
||||
}
|
||||
|
||||
if gatewayIPv6 != nil {
|
||||
defaultGWIPv6 = gatewayIPv6
|
||||
} else {
|
||||
defaultGWIPv6 = bridgeIPv6Addr
|
||||
}
|
||||
|
||||
// If linklocal IPv6
|
||||
localIPv6Net, err := linkLocalIPv6FromMac(mac.String())
|
||||
if err != nil {
|
||||
|
@ -569,7 +617,7 @@ func Allocate(id, requestedMac, requestedIP, requestedIPv6 string) (*network.Set
|
|||
|
||||
networkSettings := &network.Settings{
|
||||
IPAddress: ip.String(),
|
||||
Gateway: bridgeIPv4Network.IP.String(),
|
||||
Gateway: defaultGWIPv4.String(),
|
||||
MacAddress: mac.String(),
|
||||
Bridge: bridgeIface,
|
||||
IPPrefixLen: maskSize,
|
||||
|
@ -580,7 +628,7 @@ func Allocate(id, requestedMac, requestedIP, requestedIPv6 string) (*network.Set
|
|||
networkSettings.GlobalIPv6Address = globalIPv6.String()
|
||||
maskV6Size, _ := globalIPv6Network.Mask.Size()
|
||||
networkSettings.GlobalIPv6PrefixLen = maskV6Size
|
||||
networkSettings.IPv6Gateway = bridgeIPv6Addr.String()
|
||||
networkSettings.IPv6Gateway = defaultGWIPv6.String()
|
||||
}
|
||||
|
||||
currentInterfaces.Set(id, &networkInterface{
|
||||
|
|
|
@ -41,6 +41,12 @@ To see the man page for a command run **man docker <command>**.
|
|||
**-d**, **--daemon**=*true*|*false*
|
||||
Enable daemon mode. Default is false.
|
||||
|
||||
**--default-gateway**=""
|
||||
IPv4 address of the container default gateway; this address must be part of the bridge subnet (which is defined by \-b or \--bip)
|
||||
|
||||
**--default-gateway-v6**=""
|
||||
IPv6 address of the container default gateway
|
||||
|
||||
**--dns**=""
|
||||
Force Docker to use specific DNS servers
|
||||
|
||||
|
|
|
@ -56,6 +56,12 @@ server when it starts up, and cannot be changed once it is running:
|
|||
* `--bip=CIDR` — see
|
||||
[Customizing docker0](#docker0)
|
||||
|
||||
* `--default-gateway=IP_ADDRESS` — see
|
||||
[How Docker networks a container](#container-networking)
|
||||
|
||||
* `--default-gateway-v6=IP_ADDRESS` — see
|
||||
[IPv6](#ipv6)
|
||||
|
||||
* `--fixed-cidr` — see
|
||||
[Customizing docker0](#docker0)
|
||||
|
||||
|
@ -499,7 +505,9 @@ want to configure `eth0` via Router Advertisements you should set:
|
|||
![](/article-img/ipv6_basic_host_config.svg)
|
||||
|
||||
Every new container will get an IPv6 address from the defined subnet. Further
|
||||
a default route will be added via the gateway `fe80::1` on `eth0`:
|
||||
a default route will be added on `eth0` in the container via the address
|
||||
specified by the daemon option `--default-gateway-v6` if present, otherwise
|
||||
via `fe80::1`:
|
||||
|
||||
docker run -it ubuntu bash -c "ip -6 addr show dev eth0; ip -6 route show"
|
||||
|
||||
|
@ -865,12 +873,13 @@ The steps with which Docker configures a container are:
|
|||
parameter or generate a random one.
|
||||
|
||||
5. Give the container's `eth0` a new IP address from within the
|
||||
bridge's range of network addresses, and set its default route to
|
||||
the IP address that the Docker host owns on the bridge. The MAC
|
||||
address is generated from the IP address unless otherwise specified.
|
||||
This prevents ARP cache invalidation problems, when a new container
|
||||
comes up with an IP used in the past by another container with another
|
||||
MAC.
|
||||
bridge's range of network addresses. The default route is set to the
|
||||
IP address passed to the Docker daemon using the `--default-gateway`
|
||||
option if specified, otherwise to the IP address that the Docker host
|
||||
owns on the bridge. The MAC address is generated from the IP address
|
||||
unless otherwise specified. This prevents ARP cache invalidation
|
||||
problems, when a new container comes up with an IP used in the past by
|
||||
another container with another MAC.
|
||||
|
||||
With these steps complete, the container now possesses an `eth0`
|
||||
(virtual) network card and will find itself able to communicate with
|
||||
|
|
|
@ -116,6 +116,8 @@ expect an integer, and they can only be specified once.
|
|||
--bip="" Specify network bridge IP
|
||||
-D, --debug=false Enable debug mode
|
||||
-d, --daemon=false Enable daemon mode
|
||||
--default-gateway="" Container default gateway IPv4 address
|
||||
--default-gateway-v6="" Container default gateway IPv6 address
|
||||
--dns=[] DNS server to use
|
||||
--dns-search=[] DNS search domains to use
|
||||
-e, --exec-driver="native" Exec driver to use
|
||||
|
|
Loading…
Reference in a new issue